From eaefb8ed21ed23f732e8b608ed7948e6b71ab0d8 Mon Sep 17 00:00:00 2001 From: sakumisu <1203593632@qq.com> Date: Fri, 30 Jan 2026 22:10:34 +0800 Subject: docs: update docs and add english version Signed-off-by: sakumisu <1203593632@qq.com> --- .github/workflows/deploy-docs.yml | 4 +- .readthedocs.yaml | 35 -- README.md | 84 ++--- README_zh.md | 50 +-- docs/Makefile | 7 +- docs/en/.readthedocs.yaml | 35 ++ docs/en/api/api_config.rst | 162 +++++++++ docs/en/api/api_device.rst | 503 +++++++++++++++++++++++++++ docs/en/api/api_host.rst | 317 +++++++++++++++++ docs/en/api/api_port.rst | 266 +++++++++++++++ docs/en/api/img/api_device1.png | Bin 0 -> 296936 bytes docs/en/api/img/api_host1.png | Bin 0 -> 43480 bytes docs/en/api/img/api_host2.png | Bin 0 -> 46429 bytes docs/en/class/class_audio.rst | 4 + docs/en/class/class_cdc.rst | 4 + docs/en/class/class_hid.rst | 4 + docs/en/class/class_msc.rst | 4 + docs/en/class/class_video.rst | 4 + docs/en/class/winusb.rst | 2 + docs/en/conf.py | 37 ++ docs/en/demo/img/cherryadb.png | Bin 0 -> 42508 bytes docs/en/demo/img/otg.png | Bin 0 -> 477332 bytes docs/en/demo/img/rtt_adb_shell1.png | Bin 0 -> 67618 bytes docs/en/demo/img/rtt_adb_shell2.png | Bin 0 -> 508959 bytes docs/en/demo/img/usbh_serial.png | Bin 0 -> 3906892 bytes docs/en/demo/usb_otg.rst | 14 + docs/en/demo/usbd_adb.rst | 28 ++ docs/en/demo/usbd_audiov1.rst | 10 + docs/en/demo/usbd_audiov2.rst | 10 + docs/en/demo/usbd_cdc_acm.rst | 104 ++++++ docs/en/demo/usbd_ecm.rst | 4 + docs/en/demo/usbd_hid.rst | 4 + docs/en/demo/usbd_msc.rst | 39 +++ docs/en/demo/usbd_mtp.rst | 6 + docs/en/demo/usbd_rndis.rst | 4 + docs/en/demo/usbd_vendor.rst | 44 +++ docs/en/demo/usbd_video.rst | 83 +++++ docs/en/demo/usbd_webusb.rst | 21 ++ docs/en/demo/usbd_winusb.rst | 55 +++ docs/en/demo/usbh_audio.rst | 4 + docs/en/demo/usbh_bluetooth.rst | 2 + docs/en/demo/usbh_hid.rst | 55 +++ docs/en/demo/usbh_msc.rst | 56 +++ docs/en/demo/usbh_net.rst | 167 +++++++++ docs/en/demo/usbh_serial.rst | 196 +++++++++++ docs/en/demo/usbh_vendor.rst | 127 +++++++ docs/en/demo/usbh_video.rst | 4 + docs/en/demo/usbh_wifi.rst | 2 + docs/en/index.rst | 160 +++++++++ docs/en/quick_start/demo.rst | 313 +++++++++++++++++ docs/en/quick_start/img/env0.png | Bin 0 -> 17041 bytes docs/en/quick_start/img/env1.png | Bin 0 -> 42859 bytes docs/en/quick_start/img/env2.png | Bin 0 -> 66915 bytes docs/en/quick_start/img/esp1.png | Bin 0 -> 28939 bytes docs/en/quick_start/img/esp2.png | Bin 0 -> 72318 bytes docs/en/quick_start/img/esp3.png | Bin 0 -> 29745 bytes docs/en/quick_start/img/esp4.png | Bin 0 -> 52878 bytes docs/en/quick_start/img/question1.png | Bin 0 -> 12295 bytes docs/en/quick_start/img/question2.png | Bin 0 -> 40757 bytes docs/en/quick_start/img/stm32_1.png | Bin 0 -> 28974 bytes docs/en/quick_start/img/stm32_10.png | Bin 0 -> 8929 bytes docs/en/quick_start/img/stm32_11.png | Bin 0 -> 19428 bytes docs/en/quick_start/img/stm32_12.png | Bin 0 -> 80088 bytes docs/en/quick_start/img/stm32_13.png | Bin 0 -> 42394 bytes docs/en/quick_start/img/stm32_14.png | Bin 0 -> 32694 bytes docs/en/quick_start/img/stm32_15.png | Bin 0 -> 63453 bytes docs/en/quick_start/img/stm32_16.png | Bin 0 -> 19056 bytes docs/en/quick_start/img/stm32_18.png | Bin 0 -> 36595 bytes docs/en/quick_start/img/stm32_19.png | Bin 0 -> 44186 bytes docs/en/quick_start/img/stm32_2.png | Bin 0 -> 46511 bytes docs/en/quick_start/img/stm32_3_1.png | Bin 0 -> 36249 bytes docs/en/quick_start/img/stm32_3_2.png | Bin 0 -> 49701 bytes docs/en/quick_start/img/stm32_4_1.png | Bin 0 -> 27734 bytes docs/en/quick_start/img/stm32_4_2.png | Bin 0 -> 74975 bytes docs/en/quick_start/img/stm32_5.png | Bin 0 -> 23833 bytes docs/en/quick_start/img/stm32_6.png | Bin 0 -> 21999 bytes docs/en/quick_start/img/stm32_7.png | Bin 0 -> 8848 bytes docs/en/quick_start/img/stm32_8.png | Bin 0 -> 17224 bytes docs/en/quick_start/migration.rst | 62 ++++ docs/en/quick_start/opensource.rst | 61 ++++ docs/en/quick_start/q&a.rst | 135 ++++++++ docs/en/quick_start/rtthread.rst | 62 ++++ docs/en/quick_start/share.rst | 27 ++ docs/en/quick_start/start.rst | 52 +++ docs/en/quick_start/transplant.rst | 137 ++++++++ docs/en/show/img/usbdev_msc.png | Bin 0 -> 41061 bytes docs/en/show/img/usbdev_rndis_linux.png | Bin 0 -> 186610 bytes docs/en/show/img/usbdev_rndis_lwip.png | Bin 0 -> 61847 bytes docs/en/show/img/usbdev_rndis_lwip2.png | Bin 0 -> 418408 bytes docs/en/show/img/usbdev_rndis_wifi.png | Bin 0 -> 1000959 bytes docs/en/show/img/usbdev_rndis_wifi2.png | Bin 0 -> 295386 bytes docs/en/show/img/usbdev_rndis_win.png | Bin 0 -> 862579 bytes docs/en/show/img/usbdev_uvc_mjpeg.png | Bin 0 -> 4399953 bytes docs/en/show/img/usbdev_uvc_yuv.png | Bin 0 -> 4219553 bytes docs/en/show/img/usbhost_ax88772_1.png | Bin 0 -> 65228 bytes docs/en/show/img/usbhost_ax88772_2.png | Bin 0 -> 53080 bytes docs/en/show/img/usbhost_hub.png | Bin 0 -> 103531 bytes docs/en/show/img/usbhost_hub2.png | Bin 0 -> 11107 bytes docs/en/show/img/usbhost_msc.png | Bin 0 -> 13051 bytes docs/en/show/img/usbhost_msc_xhci.png | Bin 0 -> 40182 bytes docs/en/show/img/usbhost_rndis.png | Bin 0 -> 552961 bytes docs/en/show/img/usbhost_uvc.gif | Bin 0 -> 8564084 bytes docs/en/show/img/usbhost_wifi.png | Bin 0 -> 101688 bytes docs/en/show/index.rst | 103 ++++++ docs/en/support/img/dwc2_hostuac.png | Bin 0 -> 168135 bytes docs/en/support/img/dwc2_hostuvc1.png | Bin 0 -> 322035 bytes docs/en/support/img/dwc2_hostuvc2.png | Bin 0 -> 334772 bytes docs/en/support/img/dwc2_hostuvc3.png | Bin 0 -> 326837 bytes docs/en/support/img/ehci_hostuvc1.png | Bin 0 -> 232158 bytes docs/en/support/img/ehci_hostuvc2.png | Bin 0 -> 223817 bytes docs/en/support/img/mtpdev.png | Bin 0 -> 361577 bytes docs/en/support/img/ohci.png | Bin 0 -> 37670 bytes docs/en/support/img/rndisrx.png | Bin 0 -> 131796 bytes docs/en/support/img/rndistx.png | Bin 0 -> 147014 bytes docs/en/support/img/tmcdev1.png | Bin 0 -> 578670 bytes docs/en/support/img/tmcdev2.png | Bin 0 -> 218648 bytes docs/en/support/img/usbhost_uvc.gif | Bin 0 -> 8564084 bytes docs/en/support/index.rst | 43 +++ docs/en/tools/img/chrytool1.png | Bin 0 -> 22400 bytes docs/en/tools/img/chrytool2.png | Bin 0 -> 42418 bytes docs/en/tools/img/chrytool3.png | Bin 0 -> 21838 bytes docs/en/tools/img/chrytool4.png | Bin 0 -> 28145 bytes docs/en/tools/img/chrytool5.png | Bin 0 -> 75465 bytes docs/en/tools/img/chrytool6.png | Bin 0 -> 31559 bytes docs/en/tools/img/chrytool7.png | Bin 0 -> 35601 bytes docs/en/tools/index.rst | 49 +++ docs/en/usb/img/1.png | Bin 0 -> 107074 bytes docs/en/usb/img/10.png | Bin 0 -> 72135 bytes docs/en/usb/img/11.png | Bin 0 -> 10007 bytes docs/en/usb/img/12.png | Bin 0 -> 2125 bytes docs/en/usb/img/13.png | Bin 0 -> 2235 bytes docs/en/usb/img/14.png | Bin 0 -> 13349 bytes docs/en/usb/img/15.png | Bin 0 -> 36258 bytes docs/en/usb/img/16.png | Bin 0 -> 37965 bytes docs/en/usb/img/17.png | Bin 0 -> 47541 bytes docs/en/usb/img/18.png | Bin 0 -> 4845 bytes docs/en/usb/img/19.png | Bin 0 -> 7013 bytes docs/en/usb/img/2.png | Bin 0 -> 79045 bytes docs/en/usb/img/20.png | Bin 0 -> 74655 bytes docs/en/usb/img/21.png | Bin 0 -> 7284 bytes docs/en/usb/img/22.png | Bin 0 -> 6361 bytes docs/en/usb/img/23.png | Bin 0 -> 66450 bytes docs/en/usb/img/24.png | Bin 0 -> 19100 bytes docs/en/usb/img/25.png | Bin 0 -> 9216 bytes docs/en/usb/img/26.png | Bin 0 -> 15984 bytes docs/en/usb/img/27.png | Bin 0 -> 7785 bytes docs/en/usb/img/28.png | Bin 0 -> 6461 bytes docs/en/usb/img/29.png | Bin 0 -> 8557 bytes docs/en/usb/img/3.png | Bin 0 -> 124692 bytes docs/en/usb/img/30.png | Bin 0 -> 3724 bytes docs/en/usb/img/4.png | Bin 0 -> 168663 bytes docs/en/usb/img/5.png | Bin 0 -> 55539 bytes docs/en/usb/img/6.png | Bin 0 -> 36583 bytes docs/en/usb/img/7.png | Bin 0 -> 17216 bytes docs/en/usb/img/8.png | Bin 0 -> 72615 bytes docs/en/usb/img/9.png | Bin 0 -> 114230 bytes docs/en/usb/img/overview1.png | Bin 0 -> 92546 bytes docs/en/usb/img/overview2.png | Bin 0 -> 27578 bytes docs/en/usb/img/usb_enum.png | Bin 0 -> 175530 bytes docs/en/usb/img/usb_request.png | Bin 0 -> 81361 bytes docs/en/usb/img/usbstruct.png | Bin 0 -> 44620 bytes docs/en/usb/usb2.0_basic.rst | 294 ++++++++++++++++ docs/en/usb/usb3.0_basic.rst | 32 ++ docs/en/usb/usb_desc.rst | 37 ++ docs/en/usb/usb_enum.rst | 22 ++ docs/en/usb/usb_ext.rst | 39 +++ docs/en/usb/usb_request.rst | 6 + docs/en/usbdev.svg | 4 + docs/en/usbhost.svg | 9 + docs/en/usbip/cdns2.rst | 2 + docs/en/usbip/cdns3.rst | 2 + docs/en/usbip/chipidea.rst | 2 + docs/en/usbip/dwc2.rst | 2 + docs/en/usbip/dwc3.rst | 2 + docs/en/usbip/ehci.rst | 2 + docs/en/usbip/fotg210.rst | 2 + docs/en/usbip/musb.rst | 2 + docs/en/usbip/ohci.rst | 2 + docs/en/usbip/xhci.rst | 2 + docs/en/version.rst | 180 ++++++++++ docs/source/api/api_config.rst | 163 --------- docs/source/api/api_device.rst | 502 --------------------------- docs/source/api/api_host.rst | 317 ----------------- docs/source/api/api_port.rst | 266 --------------- docs/source/api/img/api_device1.png | Bin 296936 -> 0 bytes docs/source/api/img/api_host1.png | Bin 43480 -> 0 bytes docs/source/api/img/api_host2.png | Bin 46429 -> 0 bytes docs/source/class/class_audio.rst | 4 - docs/source/class/class_cdc.rst | 4 - docs/source/class/class_hid.rst | 4 - docs/source/class/class_msc.rst | 4 - docs/source/class/class_video.rst | 4 - docs/source/class/winusb.rst | 2 - docs/source/conf.py | 37 -- docs/source/demo/img/cherryadb.png | Bin 42508 -> 0 bytes docs/source/demo/img/otg.png | Bin 477332 -> 0 bytes docs/source/demo/img/rtt_adb_shell1.png | Bin 67618 -> 0 bytes docs/source/demo/img/rtt_adb_shell2.png | Bin 508959 -> 0 bytes docs/source/demo/img/usbh_serial.png | Bin 3906892 -> 0 bytes docs/source/demo/usb_otg.rst | 15 - docs/source/demo/usbd_adb.rst | 28 -- docs/source/demo/usbd_audiov1.rst | 7 - docs/source/demo/usbd_audiov2.rst | 9 - docs/source/demo/usbd_cdc_acm.rst | 104 ------ docs/source/demo/usbd_ecm.rst | 2 - docs/source/demo/usbd_hid.rst | 4 - docs/source/demo/usbd_msc.rst | 39 --- docs/source/demo/usbd_rndis.rst | 2 - docs/source/demo/usbd_vendor.rst | 44 --- docs/source/demo/usbd_video.rst | 83 ----- docs/source/demo/usbd_webusb.rst | 21 -- docs/source/demo/usbd_winusb.rst | 55 --- docs/source/demo/usbh_bluetooth.rst | 2 - docs/source/demo/usbh_hid.rst | 55 --- docs/source/demo/usbh_msc.rst | 56 --- docs/source/demo/usbh_net.rst | 156 --------- docs/source/demo/usbh_serial.rst | 196 ----------- docs/source/demo/usbh_vendor.rst | 127 ------- docs/source/demo/usbh_wifi.rst | 2 - docs/source/index.rst | 157 --------- docs/source/quick_start/demo.rst | 224 ------------ docs/source/quick_start/img/env0.png | Bin 17041 -> 0 bytes docs/source/quick_start/img/env1.png | Bin 42859 -> 0 bytes docs/source/quick_start/img/env2.png | Bin 66915 -> 0 bytes docs/source/quick_start/img/esp1.png | Bin 28939 -> 0 bytes docs/source/quick_start/img/esp2.png | Bin 72318 -> 0 bytes docs/source/quick_start/img/esp3.png | Bin 29745 -> 0 bytes docs/source/quick_start/img/esp4.png | Bin 52878 -> 0 bytes docs/source/quick_start/img/question1.png | Bin 12295 -> 0 bytes docs/source/quick_start/img/question2.png | Bin 40757 -> 0 bytes docs/source/quick_start/img/stm32_1.png | Bin 28974 -> 0 bytes docs/source/quick_start/img/stm32_10.png | Bin 8929 -> 0 bytes docs/source/quick_start/img/stm32_11.png | Bin 19428 -> 0 bytes docs/source/quick_start/img/stm32_12.png | Bin 80088 -> 0 bytes docs/source/quick_start/img/stm32_13.png | Bin 42394 -> 0 bytes docs/source/quick_start/img/stm32_14.png | Bin 32694 -> 0 bytes docs/source/quick_start/img/stm32_15.png | Bin 63453 -> 0 bytes docs/source/quick_start/img/stm32_16.png | Bin 19056 -> 0 bytes docs/source/quick_start/img/stm32_18.png | Bin 36595 -> 0 bytes docs/source/quick_start/img/stm32_19.png | Bin 44186 -> 0 bytes docs/source/quick_start/img/stm32_2.png | Bin 46511 -> 0 bytes docs/source/quick_start/img/stm32_3_1.png | Bin 36249 -> 0 bytes docs/source/quick_start/img/stm32_3_2.png | Bin 49701 -> 0 bytes docs/source/quick_start/img/stm32_4_1.png | Bin 27734 -> 0 bytes docs/source/quick_start/img/stm32_4_2.png | Bin 74975 -> 0 bytes docs/source/quick_start/img/stm32_5.png | Bin 23833 -> 0 bytes docs/source/quick_start/img/stm32_6.png | Bin 21999 -> 0 bytes docs/source/quick_start/img/stm32_7.png | Bin 8848 -> 0 bytes docs/source/quick_start/img/stm32_8.png | Bin 17224 -> 0 bytes docs/source/quick_start/migration.rst | 63 ---- docs/source/quick_start/opensource.rst | 62 ---- docs/source/quick_start/q&a.rst | 137 -------- docs/source/quick_start/rtthread.rst | 62 ---- docs/source/quick_start/share.rst | 27 -- docs/source/quick_start/start.rst | 53 --- docs/source/quick_start/transplant.rst | 137 -------- docs/source/show/img/usbdev_msc.png | Bin 41061 -> 0 bytes docs/source/show/img/usbdev_rndis_linux.png | Bin 186610 -> 0 bytes docs/source/show/img/usbdev_rndis_lwip.png | Bin 61847 -> 0 bytes docs/source/show/img/usbdev_rndis_lwip2.png | Bin 418408 -> 0 bytes docs/source/show/img/usbdev_rndis_wifi.png | Bin 1000959 -> 0 bytes docs/source/show/img/usbdev_rndis_wifi2.png | Bin 295386 -> 0 bytes docs/source/show/img/usbdev_rndis_win.png | Bin 862579 -> 0 bytes docs/source/show/img/usbdev_uvc_mjpeg.png | Bin 4399953 -> 0 bytes docs/source/show/img/usbdev_uvc_yuv.png | Bin 4219553 -> 0 bytes docs/source/show/img/usbhost_ax88772_1.png | Bin 65228 -> 0 bytes docs/source/show/img/usbhost_ax88772_2.png | Bin 53080 -> 0 bytes docs/source/show/img/usbhost_hub.png | Bin 103531 -> 0 bytes docs/source/show/img/usbhost_hub2.png | Bin 11107 -> 0 bytes docs/source/show/img/usbhost_msc.png | Bin 13051 -> 0 bytes docs/source/show/img/usbhost_msc_xhci.png | Bin 40182 -> 0 bytes docs/source/show/img/usbhost_rndis.png | Bin 552961 -> 0 bytes docs/source/show/img/usbhost_uvc.gif | Bin 8564084 -> 0 bytes docs/source/show/img/usbhost_wifi.png | Bin 101688 -> 0 bytes docs/source/show/index.rst | 103 ------ docs/source/support/img/dwc2_hostuac.png | Bin 168135 -> 0 bytes docs/source/support/img/dwc2_hostuvc1.png | Bin 322035 -> 0 bytes docs/source/support/img/dwc2_hostuvc2.png | Bin 334772 -> 0 bytes docs/source/support/img/dwc2_hostuvc3.png | Bin 326837 -> 0 bytes docs/source/support/img/ehci_hostuvc1.png | Bin 232158 -> 0 bytes docs/source/support/img/ehci_hostuvc2.png | Bin 223817 -> 0 bytes docs/source/support/img/mtpdev.png | Bin 361577 -> 0 bytes docs/source/support/img/ohci.png | Bin 37670 -> 0 bytes docs/source/support/img/rndisrx.png | Bin 131796 -> 0 bytes docs/source/support/img/rndistx.png | Bin 147014 -> 0 bytes docs/source/support/img/tmcdev1.png | Bin 578670 -> 0 bytes docs/source/support/img/tmcdev2.png | Bin 218648 -> 0 bytes docs/source/support/img/usbhost_uvc.gif | Bin 8564084 -> 0 bytes docs/source/support/index.rst | 43 --- docs/source/tools/img/chrytool1.png | Bin 22400 -> 0 bytes docs/source/tools/img/chrytool2.png | Bin 42418 -> 0 bytes docs/source/tools/img/chrytool3.png | Bin 21838 -> 0 bytes docs/source/tools/img/chrytool4.png | Bin 28145 -> 0 bytes docs/source/tools/img/chrytool5.png | Bin 75465 -> 0 bytes docs/source/tools/img/chrytool6.png | Bin 31559 -> 0 bytes docs/source/tools/img/chrytool7.png | Bin 35601 -> 0 bytes docs/source/tools/index.rst | 50 --- docs/source/usb/img/1.png | Bin 107074 -> 0 bytes docs/source/usb/img/10.png | Bin 72135 -> 0 bytes docs/source/usb/img/11.png | Bin 10007 -> 0 bytes docs/source/usb/img/12.png | Bin 2125 -> 0 bytes docs/source/usb/img/13.png | Bin 2235 -> 0 bytes docs/source/usb/img/14.png | Bin 13349 -> 0 bytes docs/source/usb/img/15.png | Bin 36258 -> 0 bytes docs/source/usb/img/16.png | Bin 37965 -> 0 bytes docs/source/usb/img/17.png | Bin 47541 -> 0 bytes docs/source/usb/img/18.png | Bin 4845 -> 0 bytes docs/source/usb/img/19.png | Bin 7013 -> 0 bytes docs/source/usb/img/2.png | Bin 79045 -> 0 bytes docs/source/usb/img/20.png | Bin 74655 -> 0 bytes docs/source/usb/img/21.png | Bin 7284 -> 0 bytes docs/source/usb/img/22.png | Bin 6361 -> 0 bytes docs/source/usb/img/23.png | Bin 66450 -> 0 bytes docs/source/usb/img/24.png | Bin 19100 -> 0 bytes docs/source/usb/img/25.png | Bin 9216 -> 0 bytes docs/source/usb/img/26.png | Bin 15984 -> 0 bytes docs/source/usb/img/27.png | Bin 7785 -> 0 bytes docs/source/usb/img/28.png | Bin 6461 -> 0 bytes docs/source/usb/img/29.png | Bin 8557 -> 0 bytes docs/source/usb/img/3.png | Bin 124692 -> 0 bytes docs/source/usb/img/30.png | Bin 3724 -> 0 bytes docs/source/usb/img/4.png | Bin 168663 -> 0 bytes docs/source/usb/img/5.png | Bin 55539 -> 0 bytes docs/source/usb/img/6.png | Bin 36583 -> 0 bytes docs/source/usb/img/7.png | Bin 17216 -> 0 bytes docs/source/usb/img/8.png | Bin 72615 -> 0 bytes docs/source/usb/img/9.png | Bin 114230 -> 0 bytes docs/source/usb/img/overview1.png | Bin 92546 -> 0 bytes docs/source/usb/img/overview2.png | Bin 27578 -> 0 bytes docs/source/usb/img/usb_enum.png | Bin 175530 -> 0 bytes docs/source/usb/img/usb_request.png | Bin 81361 -> 0 bytes docs/source/usb/img/usbstruct.png | Bin 44620 -> 0 bytes docs/source/usb/usb2.0_basic.rst | 296 ---------------- docs/source/usb/usb3.0_basic.rst | 33 -- docs/source/usb/usb_desc.rst | 37 -- docs/source/usb/usb_enum.rst | 22 -- docs/source/usb/usb_ext.rst | 39 --- docs/source/usb/usb_request.rst | 6 - docs/source/usbdev.svg | 4 - docs/source/usbhost.svg | 9 - docs/source/usbip/cdns2.rst | 2 - docs/source/usbip/cdns3.rst | 2 - docs/source/usbip/chipidea.rst | 2 - docs/source/usbip/dwc2.rst | 2 - docs/source/usbip/dwc3.rst | 2 - docs/source/usbip/ehci.rst | 2 - docs/source/usbip/fotg210.rst | 2 - docs/source/usbip/musb.rst | 2 - docs/source/usbip/ohci.rst | 2 - docs/source/usbip/xhci.rst | 2 - docs/source/version.rst | 182 ---------- docs/zh/.readthedocs.yaml | 35 ++ docs/zh/api/api_config.rst | 163 +++++++++ docs/zh/api/api_device.rst | 505 ++++++++++++++++++++++++++++ docs/zh/api/api_host.rst | 317 +++++++++++++++++ docs/zh/api/api_port.rst | 266 +++++++++++++++ docs/zh/api/img/api_device1.png | Bin 0 -> 296936 bytes docs/zh/api/img/api_host1.png | Bin 0 -> 43480 bytes docs/zh/api/img/api_host2.png | Bin 0 -> 46429 bytes docs/zh/class/class_audio.rst | 4 + docs/zh/class/class_cdc.rst | 4 + docs/zh/class/class_hid.rst | 4 + docs/zh/class/class_msc.rst | 4 + docs/zh/class/class_video.rst | 4 + docs/zh/class/winusb.rst | 2 + docs/zh/conf.py | 37 ++ docs/zh/demo/img/cherryadb.png | Bin 0 -> 42508 bytes docs/zh/demo/img/otg.png | Bin 0 -> 477332 bytes docs/zh/demo/img/rtt_adb_shell1.png | Bin 0 -> 67618 bytes docs/zh/demo/img/rtt_adb_shell2.png | Bin 0 -> 508959 bytes docs/zh/demo/img/usbh_serial.png | Bin 0 -> 3906892 bytes docs/zh/demo/usb_otg.rst | 15 + docs/zh/demo/usbd_adb.rst | 28 ++ docs/zh/demo/usbd_audiov1.rst | 10 + docs/zh/demo/usbd_audiov2.rst | 10 + docs/zh/demo/usbd_cdc_acm.rst | 104 ++++++ docs/zh/demo/usbd_ecm.rst | 4 + docs/zh/demo/usbd_hid.rst | 4 + docs/zh/demo/usbd_msc.rst | 39 +++ docs/zh/demo/usbd_mtp.rst | 6 + docs/zh/demo/usbd_rndis.rst | 4 + docs/zh/demo/usbd_vendor.rst | 44 +++ docs/zh/demo/usbd_video.rst | 83 +++++ docs/zh/demo/usbd_webusb.rst | 21 ++ docs/zh/demo/usbd_winusb.rst | 55 +++ docs/zh/demo/usbh_audio.rst | 4 + docs/zh/demo/usbh_bluetooth.rst | 2 + docs/zh/demo/usbh_hid.rst | 55 +++ docs/zh/demo/usbh_msc.rst | 56 +++ docs/zh/demo/usbh_net.rst | 156 +++++++++ docs/zh/demo/usbh_serial.rst | 196 +++++++++++ docs/zh/demo/usbh_vendor.rst | 127 +++++++ docs/zh/demo/usbh_video.rst | 4 + docs/zh/demo/usbh_wifi.rst | 2 + docs/zh/index.rst | 160 +++++++++ docs/zh/quick_start/demo.rst | 314 +++++++++++++++++ docs/zh/quick_start/img/env0.png | Bin 0 -> 17041 bytes docs/zh/quick_start/img/env1.png | Bin 0 -> 42859 bytes docs/zh/quick_start/img/env2.png | Bin 0 -> 66915 bytes docs/zh/quick_start/img/esp1.png | Bin 0 -> 28939 bytes docs/zh/quick_start/img/esp2.png | Bin 0 -> 72318 bytes docs/zh/quick_start/img/esp3.png | Bin 0 -> 29745 bytes docs/zh/quick_start/img/esp4.png | Bin 0 -> 52878 bytes docs/zh/quick_start/img/question1.png | Bin 0 -> 12295 bytes docs/zh/quick_start/img/question2.png | Bin 0 -> 40757 bytes docs/zh/quick_start/img/stm32_1.png | Bin 0 -> 28974 bytes docs/zh/quick_start/img/stm32_10.png | Bin 0 -> 8929 bytes docs/zh/quick_start/img/stm32_11.png | Bin 0 -> 19428 bytes docs/zh/quick_start/img/stm32_12.png | Bin 0 -> 80088 bytes docs/zh/quick_start/img/stm32_13.png | Bin 0 -> 42394 bytes docs/zh/quick_start/img/stm32_14.png | Bin 0 -> 32694 bytes docs/zh/quick_start/img/stm32_15.png | Bin 0 -> 63453 bytes docs/zh/quick_start/img/stm32_16.png | Bin 0 -> 19056 bytes docs/zh/quick_start/img/stm32_18.png | Bin 0 -> 36595 bytes docs/zh/quick_start/img/stm32_19.png | Bin 0 -> 44186 bytes docs/zh/quick_start/img/stm32_2.png | Bin 0 -> 46511 bytes docs/zh/quick_start/img/stm32_3_1.png | Bin 0 -> 36249 bytes docs/zh/quick_start/img/stm32_3_2.png | Bin 0 -> 49701 bytes docs/zh/quick_start/img/stm32_4_1.png | Bin 0 -> 27734 bytes docs/zh/quick_start/img/stm32_4_2.png | Bin 0 -> 74975 bytes docs/zh/quick_start/img/stm32_5.png | Bin 0 -> 23833 bytes docs/zh/quick_start/img/stm32_6.png | Bin 0 -> 21999 bytes docs/zh/quick_start/img/stm32_7.png | Bin 0 -> 8848 bytes docs/zh/quick_start/img/stm32_8.png | Bin 0 -> 17224 bytes docs/zh/quick_start/migration.rst | 63 ++++ docs/zh/quick_start/opensource.rst | 62 ++++ docs/zh/quick_start/q&a.rst | 137 ++++++++ docs/zh/quick_start/rtthread.rst | 62 ++++ docs/zh/quick_start/share.rst | 27 ++ docs/zh/quick_start/start.rst | 53 +++ docs/zh/quick_start/transplant.rst | 137 ++++++++ docs/zh/show/img/usbdev_msc.png | Bin 0 -> 41061 bytes docs/zh/show/img/usbdev_rndis_linux.png | Bin 0 -> 186610 bytes docs/zh/show/img/usbdev_rndis_lwip.png | Bin 0 -> 61847 bytes docs/zh/show/img/usbdev_rndis_lwip2.png | Bin 0 -> 418408 bytes docs/zh/show/img/usbdev_rndis_wifi.png | Bin 0 -> 1000959 bytes docs/zh/show/img/usbdev_rndis_wifi2.png | Bin 0 -> 295386 bytes docs/zh/show/img/usbdev_rndis_win.png | Bin 0 -> 862579 bytes docs/zh/show/img/usbdev_uvc_mjpeg.png | Bin 0 -> 4399953 bytes docs/zh/show/img/usbdev_uvc_yuv.png | Bin 0 -> 4219553 bytes docs/zh/show/img/usbhost_ax88772_1.png | Bin 0 -> 65228 bytes docs/zh/show/img/usbhost_ax88772_2.png | Bin 0 -> 53080 bytes docs/zh/show/img/usbhost_hub.png | Bin 0 -> 103531 bytes docs/zh/show/img/usbhost_hub2.png | Bin 0 -> 11107 bytes docs/zh/show/img/usbhost_msc.png | Bin 0 -> 13051 bytes docs/zh/show/img/usbhost_msc_xhci.png | Bin 0 -> 40182 bytes docs/zh/show/img/usbhost_rndis.png | Bin 0 -> 552961 bytes docs/zh/show/img/usbhost_uvc.gif | Bin 0 -> 8564084 bytes docs/zh/show/img/usbhost_wifi.png | Bin 0 -> 101688 bytes docs/zh/show/index.rst | 103 ++++++ docs/zh/support/img/dwc2_hostuac.png | Bin 0 -> 168135 bytes docs/zh/support/img/dwc2_hostuvc1.png | Bin 0 -> 322035 bytes docs/zh/support/img/dwc2_hostuvc2.png | Bin 0 -> 334772 bytes docs/zh/support/img/dwc2_hostuvc3.png | Bin 0 -> 326837 bytes docs/zh/support/img/ehci_hostuvc1.png | Bin 0 -> 232158 bytes docs/zh/support/img/ehci_hostuvc2.png | Bin 0 -> 223817 bytes docs/zh/support/img/mtpdev.png | Bin 0 -> 361577 bytes docs/zh/support/img/ohci.png | Bin 0 -> 37670 bytes docs/zh/support/img/rndisrx.png | Bin 0 -> 131796 bytes docs/zh/support/img/rndistx.png | Bin 0 -> 147014 bytes docs/zh/support/img/tmcdev1.png | Bin 0 -> 578670 bytes docs/zh/support/img/tmcdev2.png | Bin 0 -> 218648 bytes docs/zh/support/img/usbhost_uvc.gif | Bin 0 -> 8564084 bytes docs/zh/support/index.rst | 43 +++ docs/zh/tools/img/chrytool1.png | Bin 0 -> 22400 bytes docs/zh/tools/img/chrytool2.png | Bin 0 -> 42418 bytes docs/zh/tools/img/chrytool3.png | Bin 0 -> 21838 bytes docs/zh/tools/img/chrytool4.png | Bin 0 -> 28145 bytes docs/zh/tools/img/chrytool5.png | Bin 0 -> 75465 bytes docs/zh/tools/img/chrytool6.png | Bin 0 -> 31559 bytes docs/zh/tools/img/chrytool7.png | Bin 0 -> 35601 bytes docs/zh/tools/index.rst | 50 +++ docs/zh/usb/img/1.png | Bin 0 -> 107074 bytes docs/zh/usb/img/10.png | Bin 0 -> 72135 bytes docs/zh/usb/img/11.png | Bin 0 -> 10007 bytes docs/zh/usb/img/12.png | Bin 0 -> 2125 bytes docs/zh/usb/img/13.png | Bin 0 -> 2235 bytes docs/zh/usb/img/14.png | Bin 0 -> 13349 bytes docs/zh/usb/img/15.png | Bin 0 -> 36258 bytes docs/zh/usb/img/16.png | Bin 0 -> 37965 bytes docs/zh/usb/img/17.png | Bin 0 -> 47541 bytes docs/zh/usb/img/18.png | Bin 0 -> 4845 bytes docs/zh/usb/img/19.png | Bin 0 -> 7013 bytes docs/zh/usb/img/2.png | Bin 0 -> 79045 bytes docs/zh/usb/img/20.png | Bin 0 -> 74655 bytes docs/zh/usb/img/21.png | Bin 0 -> 7284 bytes docs/zh/usb/img/22.png | Bin 0 -> 6361 bytes docs/zh/usb/img/23.png | Bin 0 -> 66450 bytes docs/zh/usb/img/24.png | Bin 0 -> 19100 bytes docs/zh/usb/img/25.png | Bin 0 -> 9216 bytes docs/zh/usb/img/26.png | Bin 0 -> 15984 bytes docs/zh/usb/img/27.png | Bin 0 -> 7785 bytes docs/zh/usb/img/28.png | Bin 0 -> 6461 bytes docs/zh/usb/img/29.png | Bin 0 -> 8557 bytes docs/zh/usb/img/3.png | Bin 0 -> 124692 bytes docs/zh/usb/img/30.png | Bin 0 -> 3724 bytes docs/zh/usb/img/4.png | Bin 0 -> 168663 bytes docs/zh/usb/img/5.png | Bin 0 -> 55539 bytes docs/zh/usb/img/6.png | Bin 0 -> 36583 bytes docs/zh/usb/img/7.png | Bin 0 -> 17216 bytes docs/zh/usb/img/8.png | Bin 0 -> 72615 bytes docs/zh/usb/img/9.png | Bin 0 -> 114230 bytes docs/zh/usb/img/overview1.png | Bin 0 -> 92546 bytes docs/zh/usb/img/overview2.png | Bin 0 -> 27578 bytes docs/zh/usb/img/usb_enum.png | Bin 0 -> 175530 bytes docs/zh/usb/img/usb_request.png | Bin 0 -> 81361 bytes docs/zh/usb/img/usbstruct.png | Bin 0 -> 44620 bytes docs/zh/usb/usb2.0_basic.rst | 296 ++++++++++++++++ docs/zh/usb/usb3.0_basic.rst | 33 ++ docs/zh/usb/usb_desc.rst | 37 ++ docs/zh/usb/usb_enum.rst | 22 ++ docs/zh/usb/usb_ext.rst | 39 +++ docs/zh/usb/usb_request.rst | 6 + docs/zh/usbdev.svg | 4 + docs/zh/usbhost.svg | 9 + docs/zh/usbip/cdns2.rst | 2 + docs/zh/usbip/cdns3.rst | 2 + docs/zh/usbip/chipidea.rst | 2 + docs/zh/usbip/dwc2.rst | 2 + docs/zh/usbip/dwc3.rst | 2 + docs/zh/usbip/ehci.rst | 2 + docs/zh/usbip/fotg210.rst | 2 + docs/zh/usbip/musb.rst | 2 + docs/zh/usbip/ohci.rst | 2 + docs/zh/usbip/xhci.rst | 2 + docs/zh/version.rst | 182 ++++++++++ idf_component.yml | 2 +- 527 files changed, 8510 insertions(+), 4213 deletions(-) delete mode 100644 .readthedocs.yaml create mode 100644 docs/en/.readthedocs.yaml create mode 100755 docs/en/api/api_config.rst create mode 100755 docs/en/api/api_device.rst create mode 100755 docs/en/api/api_host.rst create mode 100755 docs/en/api/api_port.rst create mode 100755 docs/en/api/img/api_device1.png create mode 100755 docs/en/api/img/api_host1.png create mode 100755 docs/en/api/img/api_host2.png create mode 100755 docs/en/class/class_audio.rst create mode 100755 docs/en/class/class_cdc.rst create mode 100755 docs/en/class/class_hid.rst create mode 100755 docs/en/class/class_msc.rst create mode 100755 docs/en/class/class_video.rst create mode 100755 docs/en/class/winusb.rst create mode 100755 docs/en/conf.py create mode 100755 docs/en/demo/img/cherryadb.png create mode 100755 docs/en/demo/img/otg.png create mode 100755 docs/en/demo/img/rtt_adb_shell1.png create mode 100755 docs/en/demo/img/rtt_adb_shell2.png create mode 100755 docs/en/demo/img/usbh_serial.png create mode 100755 docs/en/demo/usb_otg.rst create mode 100755 docs/en/demo/usbd_adb.rst create mode 100755 docs/en/demo/usbd_audiov1.rst create mode 100755 docs/en/demo/usbd_audiov2.rst create mode 100755 docs/en/demo/usbd_cdc_acm.rst create mode 100755 docs/en/demo/usbd_ecm.rst create mode 100755 docs/en/demo/usbd_hid.rst create mode 100755 docs/en/demo/usbd_msc.rst create mode 100755 docs/en/demo/usbd_mtp.rst create mode 100755 docs/en/demo/usbd_rndis.rst create mode 100755 docs/en/demo/usbd_vendor.rst create mode 100755 docs/en/demo/usbd_video.rst create mode 100755 docs/en/demo/usbd_webusb.rst create mode 100755 docs/en/demo/usbd_winusb.rst create mode 100755 docs/en/demo/usbh_audio.rst create mode 100755 docs/en/demo/usbh_bluetooth.rst create mode 100755 docs/en/demo/usbh_hid.rst create mode 100755 docs/en/demo/usbh_msc.rst create mode 100755 docs/en/demo/usbh_net.rst create mode 100755 docs/en/demo/usbh_serial.rst create mode 100755 docs/en/demo/usbh_vendor.rst create mode 100755 docs/en/demo/usbh_video.rst create mode 100755 docs/en/demo/usbh_wifi.rst create mode 100755 docs/en/index.rst create mode 100755 docs/en/quick_start/demo.rst create mode 100755 docs/en/quick_start/img/env0.png create mode 100755 docs/en/quick_start/img/env1.png create mode 100755 docs/en/quick_start/img/env2.png create mode 100755 docs/en/quick_start/img/esp1.png create mode 100755 docs/en/quick_start/img/esp2.png create mode 100755 docs/en/quick_start/img/esp3.png create mode 100755 docs/en/quick_start/img/esp4.png create mode 100755 docs/en/quick_start/img/question1.png create mode 100755 docs/en/quick_start/img/question2.png create mode 100755 docs/en/quick_start/img/stm32_1.png create mode 100755 docs/en/quick_start/img/stm32_10.png create mode 100755 docs/en/quick_start/img/stm32_11.png create mode 100755 docs/en/quick_start/img/stm32_12.png create mode 100755 docs/en/quick_start/img/stm32_13.png create mode 100755 docs/en/quick_start/img/stm32_14.png create mode 100755 docs/en/quick_start/img/stm32_15.png create mode 100755 docs/en/quick_start/img/stm32_16.png create mode 100755 docs/en/quick_start/img/stm32_18.png create mode 100755 docs/en/quick_start/img/stm32_19.png create mode 100755 docs/en/quick_start/img/stm32_2.png create mode 100755 docs/en/quick_start/img/stm32_3_1.png create mode 100755 docs/en/quick_start/img/stm32_3_2.png create mode 100755 docs/en/quick_start/img/stm32_4_1.png create mode 100755 docs/en/quick_start/img/stm32_4_2.png create mode 100755 docs/en/quick_start/img/stm32_5.png create mode 100755 docs/en/quick_start/img/stm32_6.png create mode 100755 docs/en/quick_start/img/stm32_7.png create mode 100755 docs/en/quick_start/img/stm32_8.png create mode 100755 docs/en/quick_start/migration.rst create mode 100755 docs/en/quick_start/opensource.rst create mode 100755 docs/en/quick_start/q&a.rst create mode 100755 docs/en/quick_start/rtthread.rst create mode 100755 docs/en/quick_start/share.rst create mode 100755 docs/en/quick_start/start.rst create mode 100755 docs/en/quick_start/transplant.rst create mode 100755 docs/en/show/img/usbdev_msc.png create mode 100755 docs/en/show/img/usbdev_rndis_linux.png create mode 100755 docs/en/show/img/usbdev_rndis_lwip.png create mode 100755 docs/en/show/img/usbdev_rndis_lwip2.png create mode 100755 docs/en/show/img/usbdev_rndis_wifi.png create mode 100755 docs/en/show/img/usbdev_rndis_wifi2.png create mode 100755 docs/en/show/img/usbdev_rndis_win.png create mode 100755 docs/en/show/img/usbdev_uvc_mjpeg.png create mode 100755 docs/en/show/img/usbdev_uvc_yuv.png create mode 100755 docs/en/show/img/usbhost_ax88772_1.png create mode 100755 docs/en/show/img/usbhost_ax88772_2.png create mode 100755 docs/en/show/img/usbhost_hub.png create mode 100755 docs/en/show/img/usbhost_hub2.png create mode 100755 docs/en/show/img/usbhost_msc.png create mode 100755 docs/en/show/img/usbhost_msc_xhci.png create mode 100755 docs/en/show/img/usbhost_rndis.png create mode 100755 docs/en/show/img/usbhost_uvc.gif create mode 100755 docs/en/show/img/usbhost_wifi.png create mode 100755 docs/en/show/index.rst create mode 100755 docs/en/support/img/dwc2_hostuac.png create mode 100755 docs/en/support/img/dwc2_hostuvc1.png create mode 100755 docs/en/support/img/dwc2_hostuvc2.png create mode 100755 docs/en/support/img/dwc2_hostuvc3.png create mode 100755 docs/en/support/img/ehci_hostuvc1.png create mode 100755 docs/en/support/img/ehci_hostuvc2.png create mode 100755 docs/en/support/img/mtpdev.png create mode 100755 docs/en/support/img/ohci.png create mode 100755 docs/en/support/img/rndisrx.png create mode 100755 docs/en/support/img/rndistx.png create mode 100755 docs/en/support/img/tmcdev1.png create mode 100755 docs/en/support/img/tmcdev2.png create mode 100755 docs/en/support/img/usbhost_uvc.gif create mode 100755 docs/en/support/index.rst create mode 100755 docs/en/tools/img/chrytool1.png create mode 100755 docs/en/tools/img/chrytool2.png create mode 100755 docs/en/tools/img/chrytool3.png create mode 100755 docs/en/tools/img/chrytool4.png create mode 100755 docs/en/tools/img/chrytool5.png create mode 100755 docs/en/tools/img/chrytool6.png create mode 100755 docs/en/tools/img/chrytool7.png create mode 100755 docs/en/tools/index.rst create mode 100755 docs/en/usb/img/1.png create mode 100755 docs/en/usb/img/10.png create mode 100755 docs/en/usb/img/11.png create mode 100755 docs/en/usb/img/12.png create mode 100755 docs/en/usb/img/13.png create mode 100755 docs/en/usb/img/14.png create mode 100755 docs/en/usb/img/15.png create mode 100755 docs/en/usb/img/16.png create mode 100755 docs/en/usb/img/17.png create mode 100755 docs/en/usb/img/18.png create mode 100755 docs/en/usb/img/19.png create mode 100755 docs/en/usb/img/2.png create mode 100755 docs/en/usb/img/20.png create mode 100755 docs/en/usb/img/21.png create mode 100755 docs/en/usb/img/22.png create mode 100755 docs/en/usb/img/23.png create mode 100755 docs/en/usb/img/24.png create mode 100755 docs/en/usb/img/25.png create mode 100755 docs/en/usb/img/26.png create mode 100755 docs/en/usb/img/27.png create mode 100755 docs/en/usb/img/28.png create mode 100755 docs/en/usb/img/29.png create mode 100755 docs/en/usb/img/3.png create mode 100755 docs/en/usb/img/30.png create mode 100755 docs/en/usb/img/4.png create mode 100755 docs/en/usb/img/5.png create mode 100755 docs/en/usb/img/6.png create mode 100755 docs/en/usb/img/7.png create mode 100755 docs/en/usb/img/8.png create mode 100755 docs/en/usb/img/9.png create mode 100755 docs/en/usb/img/overview1.png create mode 100755 docs/en/usb/img/overview2.png create mode 100755 docs/en/usb/img/usb_enum.png create mode 100755 docs/en/usb/img/usb_request.png create mode 100755 docs/en/usb/img/usbstruct.png create mode 100755 docs/en/usb/usb2.0_basic.rst create mode 100755 docs/en/usb/usb3.0_basic.rst create mode 100755 docs/en/usb/usb_desc.rst create mode 100755 docs/en/usb/usb_enum.rst create mode 100755 docs/en/usb/usb_ext.rst create mode 100755 docs/en/usb/usb_request.rst create mode 100755 docs/en/usbdev.svg create mode 100755 docs/en/usbhost.svg create mode 100755 docs/en/usbip/cdns2.rst create mode 100755 docs/en/usbip/cdns3.rst create mode 100755 docs/en/usbip/chipidea.rst create mode 100755 docs/en/usbip/dwc2.rst create mode 100755 docs/en/usbip/dwc3.rst create mode 100755 docs/en/usbip/ehci.rst create mode 100755 docs/en/usbip/fotg210.rst create mode 100755 docs/en/usbip/musb.rst create mode 100755 docs/en/usbip/ohci.rst create mode 100755 docs/en/usbip/xhci.rst create mode 100755 docs/en/version.rst delete mode 100644 docs/source/api/api_config.rst delete mode 100644 docs/source/api/api_device.rst delete mode 100644 docs/source/api/api_host.rst delete mode 100644 docs/source/api/api_port.rst delete mode 100644 docs/source/api/img/api_device1.png delete mode 100644 docs/source/api/img/api_host1.png delete mode 100644 docs/source/api/img/api_host2.png delete mode 100644 docs/source/class/class_audio.rst delete mode 100644 docs/source/class/class_cdc.rst delete mode 100644 docs/source/class/class_hid.rst delete mode 100644 docs/source/class/class_msc.rst delete mode 100644 docs/source/class/class_video.rst delete mode 100644 docs/source/class/winusb.rst delete mode 100644 docs/source/conf.py delete mode 100644 docs/source/demo/img/cherryadb.png delete mode 100644 docs/source/demo/img/otg.png delete mode 100644 docs/source/demo/img/rtt_adb_shell1.png delete mode 100644 docs/source/demo/img/rtt_adb_shell2.png delete mode 100644 docs/source/demo/img/usbh_serial.png delete mode 100644 docs/source/demo/usb_otg.rst delete mode 100644 docs/source/demo/usbd_adb.rst delete mode 100644 docs/source/demo/usbd_audiov1.rst delete mode 100644 docs/source/demo/usbd_audiov2.rst delete mode 100644 docs/source/demo/usbd_cdc_acm.rst delete mode 100644 docs/source/demo/usbd_ecm.rst delete mode 100644 docs/source/demo/usbd_hid.rst delete mode 100644 docs/source/demo/usbd_msc.rst delete mode 100644 docs/source/demo/usbd_rndis.rst delete mode 100644 docs/source/demo/usbd_vendor.rst delete mode 100644 docs/source/demo/usbd_video.rst delete mode 100644 docs/source/demo/usbd_webusb.rst delete mode 100644 docs/source/demo/usbd_winusb.rst delete mode 100644 docs/source/demo/usbh_bluetooth.rst delete mode 100644 docs/source/demo/usbh_hid.rst delete mode 100644 docs/source/demo/usbh_msc.rst delete mode 100644 docs/source/demo/usbh_net.rst delete mode 100644 docs/source/demo/usbh_serial.rst delete mode 100644 docs/source/demo/usbh_vendor.rst delete mode 100644 docs/source/demo/usbh_wifi.rst delete mode 100644 docs/source/index.rst delete mode 100644 docs/source/quick_start/demo.rst delete mode 100644 docs/source/quick_start/img/env0.png delete mode 100644 docs/source/quick_start/img/env1.png delete mode 100644 docs/source/quick_start/img/env2.png delete mode 100644 docs/source/quick_start/img/esp1.png delete mode 100644 docs/source/quick_start/img/esp2.png delete mode 100644 docs/source/quick_start/img/esp3.png delete mode 100644 docs/source/quick_start/img/esp4.png delete mode 100644 docs/source/quick_start/img/question1.png delete mode 100644 docs/source/quick_start/img/question2.png delete mode 100644 docs/source/quick_start/img/stm32_1.png delete mode 100644 docs/source/quick_start/img/stm32_10.png delete mode 100644 docs/source/quick_start/img/stm32_11.png delete mode 100644 docs/source/quick_start/img/stm32_12.png delete mode 100644 docs/source/quick_start/img/stm32_13.png delete mode 100644 docs/source/quick_start/img/stm32_14.png delete mode 100644 docs/source/quick_start/img/stm32_15.png delete mode 100644 docs/source/quick_start/img/stm32_16.png delete mode 100644 docs/source/quick_start/img/stm32_18.png delete mode 100644 docs/source/quick_start/img/stm32_19.png delete mode 100644 docs/source/quick_start/img/stm32_2.png delete mode 100644 docs/source/quick_start/img/stm32_3_1.png delete mode 100644 docs/source/quick_start/img/stm32_3_2.png delete mode 100644 docs/source/quick_start/img/stm32_4_1.png delete mode 100644 docs/source/quick_start/img/stm32_4_2.png delete mode 100644 docs/source/quick_start/img/stm32_5.png delete mode 100644 docs/source/quick_start/img/stm32_6.png delete mode 100644 docs/source/quick_start/img/stm32_7.png delete mode 100644 docs/source/quick_start/img/stm32_8.png delete mode 100644 docs/source/quick_start/migration.rst delete mode 100644 docs/source/quick_start/opensource.rst delete mode 100644 docs/source/quick_start/q&a.rst delete mode 100644 docs/source/quick_start/rtthread.rst delete mode 100644 docs/source/quick_start/share.rst delete mode 100644 docs/source/quick_start/start.rst delete mode 100644 docs/source/quick_start/transplant.rst delete mode 100644 docs/source/show/img/usbdev_msc.png delete mode 100644 docs/source/show/img/usbdev_rndis_linux.png delete mode 100644 docs/source/show/img/usbdev_rndis_lwip.png delete mode 100644 docs/source/show/img/usbdev_rndis_lwip2.png delete mode 100644 docs/source/show/img/usbdev_rndis_wifi.png delete mode 100644 docs/source/show/img/usbdev_rndis_wifi2.png delete mode 100644 docs/source/show/img/usbdev_rndis_win.png delete mode 100644 docs/source/show/img/usbdev_uvc_mjpeg.png delete mode 100644 docs/source/show/img/usbdev_uvc_yuv.png delete mode 100644 docs/source/show/img/usbhost_ax88772_1.png delete mode 100644 docs/source/show/img/usbhost_ax88772_2.png delete mode 100644 docs/source/show/img/usbhost_hub.png delete mode 100644 docs/source/show/img/usbhost_hub2.png delete mode 100644 docs/source/show/img/usbhost_msc.png delete mode 100644 docs/source/show/img/usbhost_msc_xhci.png delete mode 100644 docs/source/show/img/usbhost_rndis.png delete mode 100644 docs/source/show/img/usbhost_uvc.gif delete mode 100644 docs/source/show/img/usbhost_wifi.png delete mode 100644 docs/source/show/index.rst delete mode 100644 docs/source/support/img/dwc2_hostuac.png delete mode 100644 docs/source/support/img/dwc2_hostuvc1.png delete mode 100644 docs/source/support/img/dwc2_hostuvc2.png delete mode 100644 docs/source/support/img/dwc2_hostuvc3.png delete mode 100644 docs/source/support/img/ehci_hostuvc1.png delete mode 100644 docs/source/support/img/ehci_hostuvc2.png delete mode 100644 docs/source/support/img/mtpdev.png delete mode 100644 docs/source/support/img/ohci.png delete mode 100644 docs/source/support/img/rndisrx.png delete mode 100644 docs/source/support/img/rndistx.png delete mode 100644 docs/source/support/img/tmcdev1.png delete mode 100644 docs/source/support/img/tmcdev2.png delete mode 100644 docs/source/support/img/usbhost_uvc.gif delete mode 100644 docs/source/support/index.rst delete mode 100644 docs/source/tools/img/chrytool1.png delete mode 100644 docs/source/tools/img/chrytool2.png delete mode 100644 docs/source/tools/img/chrytool3.png delete mode 100644 docs/source/tools/img/chrytool4.png delete mode 100644 docs/source/tools/img/chrytool5.png delete mode 100644 docs/source/tools/img/chrytool6.png delete mode 100644 docs/source/tools/img/chrytool7.png delete mode 100644 docs/source/tools/index.rst delete mode 100644 docs/source/usb/img/1.png delete mode 100644 docs/source/usb/img/10.png delete mode 100644 docs/source/usb/img/11.png delete mode 100644 docs/source/usb/img/12.png delete mode 100644 docs/source/usb/img/13.png delete mode 100644 docs/source/usb/img/14.png delete mode 100644 docs/source/usb/img/15.png delete mode 100644 docs/source/usb/img/16.png delete mode 100644 docs/source/usb/img/17.png delete mode 100644 docs/source/usb/img/18.png delete mode 100644 docs/source/usb/img/19.png delete mode 100644 docs/source/usb/img/2.png delete mode 100644 docs/source/usb/img/20.png delete mode 100644 docs/source/usb/img/21.png delete mode 100644 docs/source/usb/img/22.png delete mode 100644 docs/source/usb/img/23.png delete mode 100644 docs/source/usb/img/24.png delete mode 100644 docs/source/usb/img/25.png delete mode 100644 docs/source/usb/img/26.png delete mode 100644 docs/source/usb/img/27.png delete mode 100644 docs/source/usb/img/28.png delete mode 100644 docs/source/usb/img/29.png delete mode 100644 docs/source/usb/img/3.png delete mode 100644 docs/source/usb/img/30.png delete mode 100644 docs/source/usb/img/4.png delete mode 100644 docs/source/usb/img/5.png delete mode 100644 docs/source/usb/img/6.png delete mode 100644 docs/source/usb/img/7.png delete mode 100644 docs/source/usb/img/8.png delete mode 100644 docs/source/usb/img/9.png delete mode 100644 docs/source/usb/img/overview1.png delete mode 100644 docs/source/usb/img/overview2.png delete mode 100644 docs/source/usb/img/usb_enum.png delete mode 100644 docs/source/usb/img/usb_request.png delete mode 100644 docs/source/usb/img/usbstruct.png delete mode 100644 docs/source/usb/usb2.0_basic.rst delete mode 100644 docs/source/usb/usb3.0_basic.rst delete mode 100644 docs/source/usb/usb_desc.rst delete mode 100644 docs/source/usb/usb_enum.rst delete mode 100644 docs/source/usb/usb_ext.rst delete mode 100644 docs/source/usb/usb_request.rst delete mode 100644 docs/source/usbdev.svg delete mode 100644 docs/source/usbhost.svg delete mode 100644 docs/source/usbip/cdns2.rst delete mode 100644 docs/source/usbip/cdns3.rst delete mode 100644 docs/source/usbip/chipidea.rst delete mode 100644 docs/source/usbip/dwc2.rst delete mode 100644 docs/source/usbip/dwc3.rst delete mode 100644 docs/source/usbip/ehci.rst delete mode 100644 docs/source/usbip/fotg210.rst delete mode 100644 docs/source/usbip/musb.rst delete mode 100644 docs/source/usbip/ohci.rst delete mode 100644 docs/source/usbip/xhci.rst delete mode 100644 docs/source/version.rst create mode 100644 docs/zh/.readthedocs.yaml create mode 100644 docs/zh/api/api_config.rst create mode 100644 docs/zh/api/api_device.rst create mode 100644 docs/zh/api/api_host.rst create mode 100644 docs/zh/api/api_port.rst create mode 100644 docs/zh/api/img/api_device1.png create mode 100644 docs/zh/api/img/api_host1.png create mode 100644 docs/zh/api/img/api_host2.png create mode 100644 docs/zh/class/class_audio.rst create mode 100644 docs/zh/class/class_cdc.rst create mode 100644 docs/zh/class/class_hid.rst create mode 100644 docs/zh/class/class_msc.rst create mode 100644 docs/zh/class/class_video.rst create mode 100644 docs/zh/class/winusb.rst create mode 100644 docs/zh/conf.py create mode 100644 docs/zh/demo/img/cherryadb.png create mode 100644 docs/zh/demo/img/otg.png create mode 100644 docs/zh/demo/img/rtt_adb_shell1.png create mode 100644 docs/zh/demo/img/rtt_adb_shell2.png create mode 100644 docs/zh/demo/img/usbh_serial.png create mode 100644 docs/zh/demo/usb_otg.rst create mode 100644 docs/zh/demo/usbd_adb.rst create mode 100644 docs/zh/demo/usbd_audiov1.rst create mode 100644 docs/zh/demo/usbd_audiov2.rst create mode 100644 docs/zh/demo/usbd_cdc_acm.rst create mode 100644 docs/zh/demo/usbd_ecm.rst create mode 100644 docs/zh/demo/usbd_hid.rst create mode 100644 docs/zh/demo/usbd_msc.rst create mode 100644 docs/zh/demo/usbd_mtp.rst create mode 100644 docs/zh/demo/usbd_rndis.rst create mode 100644 docs/zh/demo/usbd_vendor.rst create mode 100644 docs/zh/demo/usbd_video.rst create mode 100644 docs/zh/demo/usbd_webusb.rst create mode 100644 docs/zh/demo/usbd_winusb.rst create mode 100644 docs/zh/demo/usbh_audio.rst create mode 100644 docs/zh/demo/usbh_bluetooth.rst create mode 100644 docs/zh/demo/usbh_hid.rst create mode 100644 docs/zh/demo/usbh_msc.rst create mode 100644 docs/zh/demo/usbh_net.rst create mode 100644 docs/zh/demo/usbh_serial.rst create mode 100644 docs/zh/demo/usbh_vendor.rst create mode 100644 docs/zh/demo/usbh_video.rst create mode 100644 docs/zh/demo/usbh_wifi.rst create mode 100644 docs/zh/index.rst create mode 100644 docs/zh/quick_start/demo.rst create mode 100644 docs/zh/quick_start/img/env0.png create mode 100644 docs/zh/quick_start/img/env1.png create mode 100644 docs/zh/quick_start/img/env2.png create mode 100644 docs/zh/quick_start/img/esp1.png create mode 100644 docs/zh/quick_start/img/esp2.png create mode 100644 docs/zh/quick_start/img/esp3.png create mode 100644 docs/zh/quick_start/img/esp4.png create mode 100644 docs/zh/quick_start/img/question1.png create mode 100644 docs/zh/quick_start/img/question2.png create mode 100644 docs/zh/quick_start/img/stm32_1.png create mode 100644 docs/zh/quick_start/img/stm32_10.png create mode 100644 docs/zh/quick_start/img/stm32_11.png create mode 100644 docs/zh/quick_start/img/stm32_12.png create mode 100644 docs/zh/quick_start/img/stm32_13.png create mode 100644 docs/zh/quick_start/img/stm32_14.png create mode 100644 docs/zh/quick_start/img/stm32_15.png create mode 100644 docs/zh/quick_start/img/stm32_16.png create mode 100644 docs/zh/quick_start/img/stm32_18.png create mode 100644 docs/zh/quick_start/img/stm32_19.png create mode 100644 docs/zh/quick_start/img/stm32_2.png create mode 100644 docs/zh/quick_start/img/stm32_3_1.png create mode 100644 docs/zh/quick_start/img/stm32_3_2.png create mode 100644 docs/zh/quick_start/img/stm32_4_1.png create mode 100644 docs/zh/quick_start/img/stm32_4_2.png create mode 100644 docs/zh/quick_start/img/stm32_5.png create mode 100644 docs/zh/quick_start/img/stm32_6.png create mode 100644 docs/zh/quick_start/img/stm32_7.png create mode 100644 docs/zh/quick_start/img/stm32_8.png create mode 100644 docs/zh/quick_start/migration.rst create mode 100644 docs/zh/quick_start/opensource.rst create mode 100644 docs/zh/quick_start/q&a.rst create mode 100644 docs/zh/quick_start/rtthread.rst create mode 100644 docs/zh/quick_start/share.rst create mode 100644 docs/zh/quick_start/start.rst create mode 100644 docs/zh/quick_start/transplant.rst create mode 100644 docs/zh/show/img/usbdev_msc.png create mode 100644 docs/zh/show/img/usbdev_rndis_linux.png create mode 100644 docs/zh/show/img/usbdev_rndis_lwip.png create mode 100644 docs/zh/show/img/usbdev_rndis_lwip2.png create mode 100644 docs/zh/show/img/usbdev_rndis_wifi.png create mode 100644 docs/zh/show/img/usbdev_rndis_wifi2.png create mode 100644 docs/zh/show/img/usbdev_rndis_win.png create mode 100644 docs/zh/show/img/usbdev_uvc_mjpeg.png create mode 100644 docs/zh/show/img/usbdev_uvc_yuv.png create mode 100644 docs/zh/show/img/usbhost_ax88772_1.png create mode 100644 docs/zh/show/img/usbhost_ax88772_2.png create mode 100644 docs/zh/show/img/usbhost_hub.png create mode 100644 docs/zh/show/img/usbhost_hub2.png create mode 100644 docs/zh/show/img/usbhost_msc.png create mode 100644 docs/zh/show/img/usbhost_msc_xhci.png create mode 100644 docs/zh/show/img/usbhost_rndis.png create mode 100644 docs/zh/show/img/usbhost_uvc.gif create mode 100644 docs/zh/show/img/usbhost_wifi.png create mode 100644 docs/zh/show/index.rst create mode 100644 docs/zh/support/img/dwc2_hostuac.png create mode 100644 docs/zh/support/img/dwc2_hostuvc1.png create mode 100644 docs/zh/support/img/dwc2_hostuvc2.png create mode 100644 docs/zh/support/img/dwc2_hostuvc3.png create mode 100644 docs/zh/support/img/ehci_hostuvc1.png create mode 100644 docs/zh/support/img/ehci_hostuvc2.png create mode 100644 docs/zh/support/img/mtpdev.png create mode 100644 docs/zh/support/img/ohci.png create mode 100644 docs/zh/support/img/rndisrx.png create mode 100644 docs/zh/support/img/rndistx.png create mode 100644 docs/zh/support/img/tmcdev1.png create mode 100644 docs/zh/support/img/tmcdev2.png create mode 100644 docs/zh/support/img/usbhost_uvc.gif create mode 100644 docs/zh/support/index.rst create mode 100644 docs/zh/tools/img/chrytool1.png create mode 100644 docs/zh/tools/img/chrytool2.png create mode 100644 docs/zh/tools/img/chrytool3.png create mode 100644 docs/zh/tools/img/chrytool4.png create mode 100644 docs/zh/tools/img/chrytool5.png create mode 100644 docs/zh/tools/img/chrytool6.png create mode 100644 docs/zh/tools/img/chrytool7.png create mode 100644 docs/zh/tools/index.rst create mode 100644 docs/zh/usb/img/1.png create mode 100644 docs/zh/usb/img/10.png create mode 100644 docs/zh/usb/img/11.png create mode 100644 docs/zh/usb/img/12.png create mode 100644 docs/zh/usb/img/13.png create mode 100644 docs/zh/usb/img/14.png create mode 100644 docs/zh/usb/img/15.png create mode 100644 docs/zh/usb/img/16.png create mode 100644 docs/zh/usb/img/17.png create mode 100644 docs/zh/usb/img/18.png create mode 100644 docs/zh/usb/img/19.png create mode 100644 docs/zh/usb/img/2.png create mode 100644 docs/zh/usb/img/20.png create mode 100644 docs/zh/usb/img/21.png create mode 100644 docs/zh/usb/img/22.png create mode 100644 docs/zh/usb/img/23.png create mode 100644 docs/zh/usb/img/24.png create mode 100644 docs/zh/usb/img/25.png create mode 100644 docs/zh/usb/img/26.png create mode 100644 docs/zh/usb/img/27.png create mode 100644 docs/zh/usb/img/28.png create mode 100644 docs/zh/usb/img/29.png create mode 100644 docs/zh/usb/img/3.png create mode 100644 docs/zh/usb/img/30.png create mode 100644 docs/zh/usb/img/4.png create mode 100644 docs/zh/usb/img/5.png create mode 100644 docs/zh/usb/img/6.png create mode 100644 docs/zh/usb/img/7.png create mode 100644 docs/zh/usb/img/8.png create mode 100644 docs/zh/usb/img/9.png create mode 100644 docs/zh/usb/img/overview1.png create mode 100644 docs/zh/usb/img/overview2.png create mode 100644 docs/zh/usb/img/usb_enum.png create mode 100644 docs/zh/usb/img/usb_request.png create mode 100644 docs/zh/usb/img/usbstruct.png create mode 100644 docs/zh/usb/usb2.0_basic.rst create mode 100644 docs/zh/usb/usb3.0_basic.rst create mode 100644 docs/zh/usb/usb_desc.rst create mode 100644 docs/zh/usb/usb_enum.rst create mode 100644 docs/zh/usb/usb_ext.rst create mode 100644 docs/zh/usb/usb_request.rst create mode 100644 docs/zh/usbdev.svg create mode 100644 docs/zh/usbhost.svg create mode 100644 docs/zh/usbip/cdns2.rst create mode 100644 docs/zh/usbip/cdns3.rst create mode 100644 docs/zh/usbip/chipidea.rst create mode 100644 docs/zh/usbip/dwc2.rst create mode 100644 docs/zh/usbip/dwc3.rst create mode 100644 docs/zh/usbip/ehci.rst create mode 100644 docs/zh/usbip/fotg210.rst create mode 100644 docs/zh/usbip/musb.rst create mode 100644 docs/zh/usbip/ohci.rst create mode 100644 docs/zh/usbip/xhci.rst create mode 100644 docs/zh/version.rst diff --git a/.github/workflows/deploy-docs.yml b/.github/workflows/deploy-docs.yml index 65af1f41..c02a0348 100644 --- a/.github/workflows/deploy-docs.yml +++ b/.github/workflows/deploy-docs.yml @@ -11,7 +11,7 @@ permissions: jobs: deploy: runs-on: ubuntu-latest - + steps: - uses: actions/checkout@v4 with: @@ -23,6 +23,6 @@ jobs: - uses: JamesIves/github-pages-deploy-action@v4 with: branch: gh-pages - folder: docs/build/html + folder: docs/output/zh/html diff --git a/.readthedocs.yaml b/.readthedocs.yaml deleted file mode 100644 index ed14f4de..00000000 --- a/.readthedocs.yaml +++ /dev/null @@ -1,35 +0,0 @@ -# Read the Docs configuration file for Sphinx projects -# See https://docs.readthedocs.io/en/stable/config-file/v2.html for details - -# Required -version: 2 - -# Set the OS, Python version and other tools you might need -build: - os: ubuntu-22.04 - tools: - python: "3.11" - # You can also specify other tool versions: - # nodejs: "20" - # rust: "1.70" - # golang: "1.20" - -# Build documentation in the "docs/" directory with Sphinx -sphinx: - configuration: docs/source/conf.py - # You can configure Sphinx to use a different builder, for instance use the dirhtml builder for simpler URLs - # builder: "dirhtml" - # Fail on all warnings to avoid broken references - # fail_on_warning: true - -# Optionally build your docs in additional formats such as PDF and ePub -# formats: -# - pdf -# - epub - -# Optional but recommended, declare the Python requirements required -# to build your documentation -# See https://docs.readthedocs.io/en/stable/guides/reproducible-builds.html -python: - install: - - requirements: docs/requirements.txt \ No newline at end of file diff --git a/README.md b/README.md index d514f1fb..24b55277 100644 --- a/README.md +++ b/README.md @@ -14,31 +14,31 @@ CherryUSB is a tiny and beautiful, high performance and portable USB host and de ## Why choose CherryUSB -### Easy to study USB +### Easy to Learn USB -In order to make it easier for users to learn USB basics, enumeration, driver loading and IP drivers, the code has been written with the following advantages: +To facilitate user learning of USB fundamentals, enumeration, driver loading, and IP drivers, the written code has the following advantages: -- Lean code, simple logic, no complex C syntax -- Tree-based programming with cascading code -- Class-drivers and porting-drivers are templating and simplification -- Clear API classification (slave: initialisation, registration api, command callback api, data sending and receiving api; host: initialisation, lookup api, data sending and receiving api) +- Streamlined code with simple logic and no complex C language syntax +- Tree-structured programming with progressive code layers +- Templated and simplified Class drivers and porting drivers +- Clear API categorization (Device: initialization, class registration, command callbacks, data transmission; Host: initialization, class discovery, data transmission) -### Easy to use USB +### Easy to Use USB -In order to facilitate the use of the USB interface and to take into account the fact that users have learned about uart and dma, the following advantages have been designed for the data sending and receiving class of interface: +To facilitate user interaction with USB interfaces, considering users’ familiarity with UART and DMA, the designed data transmission interface has the following advantages: -- Equivalent to using uart tx dma/uart rx dma -- There is no limit to the length of send and receive, the user does not need to care about the USB packetization process (the porting driver does it) +- Equivalent to using UART TX DMA/UART RX DMA +- No length restrictions on transmission/reception; users don’t need to worry about USB packetization (porting drivers handle packetization) -### Easy to bring out USB performance +### Easy to Achieve USB Performance -Taking into account USB performance issues and trying to achieve the theoretical bandwidth of the USB hardware, the design of the data transceiver class interface has the following advantages: +Considering USB performance requirements to reach theoretical USB hardware bandwidth, the designed data transmission interface has the following advantages: -- Porting drivers directly to registers, no abstraction layer encapsulation +- Porting drivers directly interface with registers without abstraction layer encapsulation - Memory zero copy -- If IP has DMA then uses DMA mode (DMA with hardware packetization) -- Unlimited length make it easier to interface with hardware DMA and take advantage of DMA -- Packetization is handled in interrupt +- DMA mode used when IP supports DMA (DMA provides hardware packetization functionality) +- No length restrictions, facilitating hardware DMA interfacing and maximizing DMA advantages +- Packetization handled in interrupt context Performance show:https://cherryusb.cherry-embedded.org/show/ @@ -176,55 +176,31 @@ Only standard and commercial USB IP are listed. | CDNS3(cadence) | CDNS3 | XHCI | × | | DWC3(synopsys) | DWC3 | XHCI | × | -## Documentation Tutorial +## Resources -Quickly start, USB basic concepts, API manual, Class basic concepts and examples, see [CherryUSB Documentation Tutorial](https://cherryusb.readthedocs.io/). +### Getting Started -## Video Tutorial +- 📖 [CherryUSB Documentation](https://cherryusb.readthedocs.io/en/latest/) +- 💻 [CherryUSB Demo Repo](https://cherryusb.readthedocs.io/en/latest/quick_start/demo.html) +- 📺 [CherryUSB Cheese(>= V1.4.3)](https://www.bilibili.com/cheese/play/ss707687201) -CherryUSB Cheese (>= V1.4.3): https://www.bilibili.com/cheese/play/ss707687201 . - -## Descriptor Generator Tool - -Cherry Descriptor: https://desc.cherry-embedded.org/en - -## Demo Repo - -| Manufacturer | CHIP or Series | USB IP| Repo Url | Support version | Note | -|:--------------------:|:------------------:|:-----:|:--------:|:------------------:|:-------------:| -|Bouffalolab | BL702/BL616/BL808 | bouffalolab/ehci|[bouffalo_sdk](https://github.com/CherryUSB/bouffalo_sdk)|<= latest | Official | -|ST | STM32F1x/STM32F4/STM32H7 | fsdev/dwc2 |[stm32_repo](https://github.com/CherryUSB/cherryusb_stm32)|<= latest | Community | -|HPMicro | HPM6000/HPM5000 | hpm/ehci |[hpm_sdk](https://github.com/CherryUSB/hpm_sdk)|<= latest | Official | -|Essemi | ES32F36xx | musb |[es32f369_repo](https://github.com/CherryUSB/cherryusb_es32)|<= latest | Official | -|Phytium | e2000 | pusb2/xhci |[phytium_repo](https://gitee.com/phytium_embedded/phytium-free-rtos-sdk)|>=1.4.0 | Official | -|Artinchip | d12x/d13x/d21x | aic/ehci/ohci |[luban-lite](https://gitee.com/artinchip/luban-lite)|<= latest | Official | -|Espressif | esp32s2/esp32s3/esp32p4 | dwc2 |[esp32_repo](https://github.com/CherryUSB/cherryusb_esp32)/[espressif](https://github.com/espressif/esp-idf/tree/master/examples/peripherals/usb)|<= latest | Official | -|Kendryte | k230 | dwc2 |[k230_repo](https://github.com/CherryUSB/k230_sdk)|v1.2.0 | Official | -|Actionstech | ATS30xx | dwc2 |[action_zephyr_repo](https://github.com/CherryUSB/lv_port_actions_technology/tree/master/action_technology_sdk)|>=1.4.0 | Official | -|SiFli | SF32LB5x | musb |[SiFli_sdk](https://github.com/OpenSiFli/SiFli-SDK)|>=1.5.0 | Official | -|NXP | mcx | kinetis/chipidea/ehci |[nxp_mcx_repo](https://github.com/CherryUSB/cherryusb_mcx)|<= latest | Community | -|Nationstech | n32h4x | dwc2 |[nation_repo](https://github.com/CherryUSB/cherryusb_nation)|>=1.5.0 | Official ongoing | -|Raspberry pi | rp2040/rp2350 | rp2040 |[pico-sdk](https://github.com/CherryUSB/pico-sdk)|<= latest | Official ongoing | -|AllwinnerTech | F1C100S/F1C200S | musb |[cherryusb_rtt_f1c100s](https://github.com/CherryUSB/cherryusb_rtt_f1c100s)|<= latest | no more update | -|Bekencorp | bk7256/bk7258 | musb |[bk_idk](https://github.com/CherryUSB/bk_idk)| v0.7.0 | Official | -|Sophgo | cv18xx | dwc2 |[cvi_alios_open](https://github.com/CherryUSB/cvi_alios_open)| v0.7.0 | Official | -|WCH | CH32V307/ch58x | ch32_usbfs/ch32_usbhs/ch58x |[wch_repo](https://github.com/CherryUSB/cherryusb_wch)|<= v0.10.2/>=v1.5.0 | no more update | - -## Package Support - -CherryUSB package is available as follows: +### Package Support - [RT-Thread](https://packages.rt-thread.org/detail.html?package=CherryUSB) - [YOC](https://www.xrvm.cn/document?temp=usb-host-protocol-stack-device-driver-adaptation-instructions&slug=yocbook) - [ESP-Registry](https://components.espressif.com/components/cherry-embedded/cherryusb) -## Commercial Support +### Descriptor Generator Tool -Refer to https://cherryusb.readthedocs.io/zh-cn/latest/support/index.html. +Cherry Descriptor: https://desc.cherry-embedded.org/en + +### Contact -## Contact +CherryUSB discord: https://discord.com/invite/wFfvrSAey8 + +## Commercial Support -CherryUSB discord: https://discord.com/invite/wFfvrSAey8. +Refer to https://cherryusb.readthedocs.io/en/latest/support/index.html ## Company Support diff --git a/README_zh.md b/README_zh.md index cf76f3ea..b4b60472 100644 --- a/README_zh.md +++ b/README_zh.md @@ -176,58 +176,34 @@ x 受以下宏影响: | CDNS3(cadence) | CDNS3 | XHCI | × | | DWC3(synopsys) | DWC3 | XHCI | × | -## 文档教程 +## Resources -CherryUSB 快速入门、USB 基本概念、API 手册、Class 基本概念和例程,参考 [CherryUSB Documentation Tutorial](https://cherryusb.readthedocs.io/)。 +### 快速开始 -## 视频教程 +- 📖 [CherryUSB Documentation](https://cherryusb.readthedocs.io/zh-cn/latest/) +- 💻 [CherryUSB Demo Repo](https://cherryusb.readthedocs.io/zh-cn/latest/quick_start/demo.html) +- 📺 [CherryUSB Cheese(>= V1.4.3)](https://www.bilibili.com/cheese/play/ss707687201) -CherryUSB 课程(>= V1.4.3):https://www.bilibili.com/cheese/play/ss707687201 。 - -## 描述符生成工具 - -Cherry Descriptor: https://desc.cherry-embedded.org/zh - -## 示例仓库 - -| Manufacturer | CHIP or Series | USB IP| Repo Url | Support version | Note | -|:--------------------:|:------------------:|:-----:|:--------:|:------------------:|:-------------:| -|Bouffalolab | BL702/BL616/BL808 | bouffalolab/ehci|[bouffalo_sdk](https://github.com/CherryUSB/bouffalo_sdk)|<= latest | Official | -|ST | STM32F1x/STM32F4/STM32H7 | fsdev/dwc2 |[stm32_repo](https://github.com/CherryUSB/cherryusb_stm32)|<= latest | Community | -|HPMicro | HPM6000/HPM5000 | hpm/ehci |[hpm_sdk](https://github.com/CherryUSB/hpm_sdk)|<= latest | Official | -|Essemi | ES32F36xx | musb |[es32f369_repo](https://github.com/CherryUSB/cherryusb_es32)|<= latest | Official | -|Phytium | e2000 | pusb2/xhci |[phytium_repo](https://gitee.com/phytium_embedded/phytium-free-rtos-sdk)|>=1.4.0 | Official | -|Artinchip | d12x/d13x/d21x | aic/ehci/ohci |[luban-lite](https://gitee.com/artinchip/luban-lite)|<= latest | Official | -|Espressif | esp32s2/esp32s3/esp32p4 | dwc2 |[esp32_repo](https://github.com/CherryUSB/cherryusb_esp32)/[espressif](https://github.com/espressif/esp-idf/tree/master/examples/peripherals/usb)|<= latest | Official | -|Kendryte | k230 | dwc2 |[k230_repo](https://github.com/CherryUSB/k230_sdk)|v1.2.0 | Official | -|Actionstech | ATS30xx | dwc2 |[action_zephyr_repo](https://github.com/CherryUSB/lv_port_actions_technology/tree/master/action_technology_sdk)|>=1.4.0 | Official | -|SiFli | SF32LB5x | musb |[SiFli_sdk](https://github.com/OpenSiFli/SiFli-SDK)|>=1.5.0 | Official | -|NXP | mcx | kinetis/chipidea/ehci |[nxp_mcx_repo](https://github.com/CherryUSB/cherryusb_mcx)|<= latest | Community | -|Nationstech | n32h4x | dwc2 |[nation_repo](https://github.com/CherryUSB/cherryusb_nation)|>=1.5.0 | Official ongoing | -|Raspberry pi | rp2040/rp2350 | rp2040 |[pico-sdk](https://github.com/CherryUSB/pico-sdk)|<= latest | Official ongoing | -|AllwinnerTech | F1C100S/F1C200S | musb |[cherryusb_rtt_f1c100s](https://github.com/CherryUSB/cherryusb_rtt_f1c100s)|<= latest | no more update | -|Bekencorp | bk7256/bk7258 | musb |[bk_idk](https://github.com/CherryUSB/bk_idk)| v0.7.0 | Official | -|Sophgo | cv18xx | dwc2 |[cvi_alios_open](https://github.com/CherryUSB/cvi_alios_open)| v0.7.0 | Official | -|WCH | CH32V307/ch58x | ch32_usbfs/ch32_usbhs/ch58x |[wch_repo](https://github.com/CherryUSB/cherryusb_wch)|<= v0.10.2/>=v1.5.0 | no more update | - -## 软件包支持 - -CherryUSB 软件包可以通过以下方式获取: +### 软件包支持 - [RT-Thread](https://packages.rt-thread.org/detail.html?package=CherryUSB) - [YOC](https://www.xrvm.cn/document?temp=usb-host-protocol-stack-device-driver-adaptation-instructions&slug=yocbook) - [ESP-Registry](https://components.espressif.com/components/cherry-embedded/cherryusb) -## 商业支持 +### 描述符生成工具 -参考 https://cherryusb.readthedocs.io/zh-cn/latest/support/index.html 。 +Cherry Descriptor: https://desc.cherry-embedded.org/zh -## 联系 +### Contact CherryUSB QQ群:642693751 CherryUSB 微信群:与我联系后邀请加入 +## 商业支持 + +参考 https://cherryusb.readthedocs.io/zh-cn/latest/support/index.html + ## 支持企业 感谢以下企业支持(顺序不分先后): diff --git a/docs/Makefile b/docs/Makefile index d0c3cbf1..3c4d6efb 100644 --- a/docs/Makefile +++ b/docs/Makefile @@ -5,16 +5,15 @@ # from the environment for the first two. SPHINXOPTS ?= SPHINXBUILD ?= sphinx-build -SOURCEDIR = source -BUILDDIR = build # Put it first so that "make" without argument is like "make help". help: - @$(SPHINXBUILD) -M help "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O) + @$(SPHINXBUILD) -M help .PHONY: help Makefile # Catch-all target: route all unknown targets to Sphinx using the new # "make mode" option. $(O) is meant as a shortcut for $(SPHINXOPTS). %: Makefile - @$(SPHINXBUILD) -M $@ "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O) + @$(SPHINXBUILD) -M html "zh" "output/zh" $(SPHINXOPTS) $(O) + @$(SPHINXBUILD) -M html "en" "output/en" $(SPHINXOPTS) $(O) diff --git a/docs/en/.readthedocs.yaml b/docs/en/.readthedocs.yaml new file mode 100644 index 00000000..31a7d30a --- /dev/null +++ b/docs/en/.readthedocs.yaml @@ -0,0 +1,35 @@ +# Read the Docs configuration file for Sphinx projects +# See https://docs.readthedocs.io/en/stable/config-file/v2.html for details + +# Required +version: 2 + +# Set the OS, Python version and other tools you might need +build: + os: ubuntu-22.04 + tools: + python: "3.11" + # You can also specify other tool versions: + # nodejs: "20" + # rust: "1.70" + # golang: "1.20" + +# Build documentation in the "docs/" directory with Sphinx +sphinx: + configuration: docs/en/conf.py + # You can configure Sphinx to use a different builder, for instance use the dirhtml builder for simpler URLs + # builder: "dirhtml" + # Fail on all warnings to avoid broken references + # fail_on_warning: true + +# Optionally build your docs in additional formats such as PDF and ePub +# formats: +# - pdf +# - epub + +# Optional but recommended, declare the Python requirements required +# to build your documentation +# See https://docs.readthedocs.io/en/stable/guides/reproducible-builds.html +python: + install: + - requirements: docs/requirements.txt \ No newline at end of file diff --git a/docs/en/api/api_config.rst b/docs/en/api/api_config.rst new file mode 100755 index 00000000..f1fed77a --- /dev/null +++ b/docs/en/api/api_config.rst @@ -0,0 +1,162 @@ +USB CONFIG Description +======================================= + +General CONFIG +--------------------- + +CONFIG_USB_PRINTF +^^^^^^^^^^^^^^^^^^^^ + +USB log functionality, defaults to redirect to printf. Note that USB log will be used in interrupts, so the redirected API must not block. For example, if using RT-Thread, please change to rt-kprintf + +CONFIG_USB_DBG_LEVEL +^^^^^^^^^^^^^^^^^^^^^^ + +Controls the log print level + +CONFIG_USB_PRINTF_COLOR_ENABLE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Controls log color printing, enabled by default + +CONFIG_USB_DCACHE_ENABLE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +When not using nocache RAM, enable this macro to ensure data consistency. **When using EHCI, nocache RAM is still required internally**. + +CONFIG_USB_ALIGN_SIZE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +USB buffer alignment size, default is 4. IP in DMA mode may have alignment requirements for input buffers, typically 4. If other alignment is needed, please modify this value. + +USB_NOCACHE_RAM_SECTION +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +If the chip doesn't have cache functionality, this macro is ineffective. If it does, USB input/output buffers must be placed in nocache RAM to ensure data consistency. + +Device Protocol Stack CONFIG +------------------------------ + +CONFIG_USBDEV_REQUEST_BUFFER_LEN +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Controls the maximum length of control transfer receive and send buffer, default is 512. + +CONFIG_USBDEV_SETUP_LOG_PRINT +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Enable or disable setup packet dump information, disabled by default. + +CONFIG_USBDEV_DESC_CHECK +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Not implemented yet + +CONFIG_USBDEV_TEST_MODE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +Enable or disable USB test mode + +CONFIG_USBDEV_MSC_MAX_BUFSIZE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Maximum length of MSC cache. Larger cache results in higher USB speed because storage media typically has much higher multi-block read/write speeds than single block, such as SD cards. +Default 512. For flash, needs to be changed to 4K. Cache size must be a multiple of the storage media's block size. + +CONFIG_USBDEV_MSC_MANUFACTURER_STRING +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +CONFIG_USBDEV_MSC_PRODUCT_STRING +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +CONFIG_USBDEV_MSC_VERSION_STRING +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +CONFIG_USBDEV_MSC_POLLING +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Run usbd_msc_sector_read and usbd_msc_sector_write operations in while1, used in bare-metal systems. + +CONFIG_USBDEV_MSC_THREAD +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Enable or disable MSC thread, disabled by default. usbd_msc_sector_read and usbd_msc_sector_write are executed in interrupts by default, so if OS is enabled, it's recommended to enable this macro, then usbd_msc_sector_read and usbd_msc_sector_write will execute in threads. + +CONFIG_USBDEV_MSC_PRIO +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Priority of MSC read/write thread, default is 4. Lower values mean higher priority. + +CONFIG_USBDEV_MSC_STACKSIZE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Stack size of MSC read/write thread, default 2K bytes + +CONFIG_USBDEV_RNDIS_RESP_BUFFER_SIZE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Maximum receive and send length for RNDIS control transfers. Minimum length determined by RNDIS options list, default should be greater than or equal to 156. + +CONFIG_USBDEV_RNDIS_ETH_MAX_FRAME_SIZE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Maximum length of RNDIS Ethernet frame, default 1580 + +CONFIG_USBDEV_RNDIS_VENDOR_ID +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +CONFIG_USBDEV_RNDIS_VENDOR_DESC +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +CONFIG_USBDEV_RNDIS_USING_LWIP +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +RNDIS interface with LWIP + +Host Protocol Stack CONFIG +---------------------------- + +The following parameters determine the maximum number of supported external hubs, interfaces, endpoints per interface, and altsetting counts. Changing these values affects RAM size, it's recommended to adjust according to actual requirements. + +.. code-block:: C + + #define CONFIG_USBHOST_MAX_RHPORTS 1 + #define CONFIG_USBHOST_MAX_EXTHUBS 1 + #define CONFIG_USBHOST_MAX_EHPORTS 4 + #define CONFIG_USBHOST_MAX_INTERFACES 6 + #define CONFIG_USBHOST_MAX_INTF_ALTSETTINGS 1 + #define CONFIG_USBHOST_MAX_ENDPOINTS 4 + +The following parameters determine the maximum number of supported class drivers. Changing these values affects RAM size, it's recommended to adjust according to actual requirements. + +.. code-block:: C + + #define CONFIG_USBHOST_MAX_SERIAL_CLASS 4 + #define CONFIG_USBHOST_MAX_HID_CLASS 4 + #define CONFIG_USBHOST_MAX_MSC_CLASS 2 + #define CONFIG_USBHOST_MAX_AUDIO_CLASS 1 + #define CONFIG_USBHOST_MAX_VIDEO_CLASS 1 + +CONFIG_USBHOST_PSC_PRIO +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Priority of host plug/unplug thread, default is 0. Lower values mean higher priority. + +CONFIG_USBHOST_PSC_STACKSIZE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Stack size of host plug/unplug thread, default 2K bytes + +CONFIG_USBHOST_REQUEST_BUFFER_LEN +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Maximum length for control transfer receive or send + +CONFIG_USBHOST_CONTROL_TRANSFER_TIMEOUT +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Timeout for control transfer send or receive, default 500 ms + +CONFIG_USBHOST_MSC_TIMEOUT +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Timeout for MSC read/write transfers, default 5s \ No newline at end of file diff --git a/docs/en/api/api_device.rst b/docs/en/api/api_device.rst new file mode 100755 index 00000000..f44be9dd --- /dev/null +++ b/docs/en/api/api_device.rst @@ -0,0 +1,503 @@ +Device Protocol Stack +======================================= + +The device protocol stack is mainly responsible for enumeration and driver loading. We won't discuss enumeration here, but for driver loading (i.e., interface driver loading), it mainly relies on the `usbd_add_interface` function to record the passed-in interface driver and save it to the interface array table. When the host makes class requests, it can search the interface table for access. +After calling `usbd_desc_register`, interface registration and endpoint registration need to be performed according to the following rules: + +- Call `usbd_add_interface` as many times as there are interfaces, with parameters filling in the relevant `xxx_init_intf`. If not supported, manually create an intf and fill it in +- Call `usbd_add_endpoint` as many times as there are endpoints. When interrupts complete, the registered endpoint callback will be called. + +Refer to the diagram below: + +.. figure:: img/api_device1.png + +CORE +----------------- + +Endpoint Structure +"""""""""""""""""""""""""""""""""""" + +The endpoint structure is mainly used to register interrupt completion callback functions for different endpoint addresses. + +.. code-block:: C + + struct usbd_endpoint { + uint8_t ep_addr; + usbd_endpoint_callback ep_cb; + }; + +- **ep_addr** Endpoint address (with direction) +- **ep_cb** Endpoint completion interrupt callback function. + +.. note:: To summarize in one sentence: in callback function is equivalent to DMA transmission completion interrupt callback function; out callback function is equivalent to DMA reception completion interrupt callback function + +Interface Structure +"""""""""""""""""""""""""""""""""""" + +The interface structure is mainly used to register requests other than standard device requests for different class devices, including class device requests, vendor device requests, and custom device requests, as well as related notification callback functions in the protocol stack. + +.. code-block:: C + + struct usbd_interface { + usbd_request_handler class_interface_handler; + usbd_request_handler class_endpoint_handler; + usbd_request_handler vendor_handler; + usbd_notify_handler notify_handler; + const uint8_t *hid_report_descriptor; + uint32_t hid_report_descriptor_len; + uint8_t intf_num; + }; + +- **class_interface_handler** class setup request callback function, recipient is interface +- **class_endpoint_handler** class setup request callback function, recipient is endpoint +- **vendor_handler** vendor setup request callback function +- **notify_handler** interrupt flag, protocol stack related status callback function +- **hid_report_descriptor** hid report descriptor +- **hid_report_descriptor_len** hid report descriptor length +- **intf_num** current interface offset + +usbd_desc_register +"""""""""""""""""""""""""""""""""""" + +``usbd_desc_register`` is used to register USB descriptors. Descriptor types include: device descriptor, configuration descriptor (including configuration descriptor, interface descriptor, class descriptor, endpoint descriptor), string descriptor, device qualifier descriptor, other speed descriptor, BOS descriptor, WinUSB descriptor. + +.. code-block:: C + + // Enable CONFIG_USBDEV_ADVANCE_DESC + void usbd_desc_register(uint8_t busid, const struct usb_descriptor *desc); + + // Disable CONFIG_USBDEV_ADVANCE_DESC + void usbd_desc_register(uint8_t busid, const uint8_t *desc); + void usbd_msosv1_desc_register(uint8_t busid, struct usb_msosv1_descriptor *desc); + void usbd_msosv2_desc_register(uint8_t busid, struct usb_msosv2_descriptor *desc); + void usbd_bos_desc_register(uint8_t busid, struct usb_bos_descriptor *desc); + void usbd_webusb_desc_register(uint8_t busid, struct usb_webusb_descriptor *desc); + +- **desc** Descriptor handle + +.. note:: Currently CONFIG_USBDEV_ADVANCE_DESC is enabled by default. If you need to use the old version API, please disable this macro. Starting from v1.6.0, only APIs with CONFIG_USBDEV_ADVANCE_DESC enabled are available + +usbd_add_interface +"""""""""""""""""""""""""""""""""""" + +``usbd_add_interface`` adds an interface driver. **The addition order must follow the interface order in the descriptor**. + +.. code-block:: C + + void usbd_add_interface(uint8_t busid, struct usbd_interface *intf); + +- **busid** USB bus ID +- **intf** Interface driver handle, usually obtained from different class `xxx_init_intf` functions + +usbd_add_endpoint +"""""""""""""""""""""""""""""""""""" + +``usbd_add_endpoint`` adds an endpoint interrupt completion callback function. + +.. code-block:: C + + void usbd_add_endpoint(uint8_t busid, struct usbd_endpoint *ep); + +- **busid** USB bus ID +- **ep** Endpoint handle + +usbd_initialize +"""""""""""""""""""""""""""""""""""" + +``usbd_initialize`` is used to initialize USB device register configuration, USB clock, interrupts, etc. Note that this function must be called last after registering descriptor APIs. **If using an OS, it must be executed within a thread**. + +.. code-block:: C + + int usbd_initialize(uint8_t busid, uintptr_t reg_base, usbd_event_handler_t event_handler); + +- **busid** USB bus ID +- **reg_base** USB device register base address +- **event_handler** Protocol stack interrupt or status callback function, event events +- **return** Returns 0 for success, other values indicate failure + +Event events include: + +.. code-block:: C + + USBD_EVENT_ERROR, /** USB error reported by the controller */ + USBD_EVENT_RESET, /** USB reset */ + USBD_EVENT_SOF, /** Start of Frame received */ + USBD_EVENT_CONNECTED, /** USB connected*/ + USBD_EVENT_DISCONNECTED, /** USB disconnected */ + USBD_EVENT_SUSPEND, /** USB connection suspended by the HOST */ + USBD_EVENT_RESUME, /** USB connection resumed by the HOST */ + + /* USB DEVICE STATUS */ + USBD_EVENT_CONFIGURED, /** USB configuration done */ + USBD_EVENT_SET_INTERFACE, /** USB interface selected */ + USBD_EVENT_SET_REMOTE_WAKEUP, /** USB set remote wakeup */ + USBD_EVENT_CLR_REMOTE_WAKEUP, /** USB clear remote wakeup */ + USBD_EVENT_INIT, /** USB init done when call usbd_initialize */ + USBD_EVENT_DEINIT, /** USB deinit done when call usbd_deinitialize */ + USBD_EVENT_UNKNOWN + +.. note:: Most IPs do not support USBD_EVENT_CONNECTED and USBD_EVENT_DISCONNECTED events. Currently only HPM chips support them. For other chips, design your own VBUS detection circuit as an alternative + +usbd_deinitialize +"""""""""""""""""""""""""""""""""""" + +``usbd_deinitialize`` is used to deinitialize USB device, turn off USB device clock, interrupts, etc. + +.. code-block:: C + + int usbd_deinitialize(uint8_t busid); + +- **busid** USB bus ID +- **return** Returns 0 for success, other values indicate failure + +CDC ACM +----------------- + +usbd_cdc_acm_init_intf +"""""""""""""""""""""""""""""""""""" + +``usbd_cdc_acm_init_intf`` is used to initialize USB CDC ACM class interface and implement related functions for this interface. + +- ``cdc_acm_class_interface_request_handler`` is used to handle USB CDC ACM class Setup requests. +- ``cdc_notify_handler`` is used to handle other USB CDC interrupt callback functions. + +.. code-block:: C + + struct usbd_interface *usbd_cdc_acm_init_intf(uint8_t busid, struct usbd_interface *intf); + +- **busid** USB bus ID +- **return** Interface handle + +usbd_cdc_acm_set_line_coding +"""""""""""""""""""""""""""""""""""" + +``usbd_cdc_acm_set_line_coding`` is used to configure the serial port. If only using USB without serial port, this interface does not need to be implemented by the user and can use the default. + +.. code-block:: C + + void usbd_cdc_acm_set_line_coding(uint8_t busid, uint8_t intf, struct cdc_line_coding *line_coding); + +- **busid** USB bus ID +- **intf** Control interface number +- **line_coding** Serial port configuration + +usbd_cdc_acm_get_line_coding +"""""""""""""""""""""""""""""""""""" + +``usbd_cdc_acm_get_line_coding`` is used to get serial port configuration. If only using USB without serial port, this interface does not need to be implemented by the user and can use the default. + +.. code-block:: C + + void usbd_cdc_acm_get_line_coding(uint8_t busid, uint8_t intf, struct cdc_line_coding *line_coding); + +- **busid** USB bus ID +- **intf** Control interface number +- **line_coding** Serial port configuration + +usbd_cdc_acm_set_dtr +"""""""""""""""""""""""""""""""""""" + +``usbd_cdc_acm_set_dtr`` is used to control serial port DTR. If only using USB without serial port, this interface does not need to be implemented by the user and can use the default. + +.. code-block:: C + + void usbd_cdc_acm_set_dtr(uint8_t busid, uint8_t intf, bool dtr); + +- **busid** USB bus ID +- **intf** Control interface number +- **dtr** dtr = 1 means pull low level, 0 means pull high level + +usbd_cdc_acm_set_rts +"""""""""""""""""""""""""""""""""""" + +``usbd_cdc_acm_set_rts`` is used to control serial port RTS. If only using USB without serial port, this interface does not need to be implemented by the user and can use the default. + +.. code-block:: C + + void usbd_cdc_acm_set_rts(uint8_t busid, uint8_t intf, bool rts); + +- **busid** USB bus ID +- **intf** Control interface number +- **rts** rts = 1 means pull low level, 0 means pull high level + +CDC_ACM_DESCRIPTOR_INIT +"""""""""""""""""""""""""""""""""""" + +``CDC_ACM_DESCRIPTOR_INIT`` configures the default CDC ACM required descriptors and parameters for user convenience. Total length is `CDC_ACM_DESCRIPTOR_LEN`. + +.. code-block:: C + + CDC_ACM_DESCRIPTOR_INIT(bFirstInterface, int_ep, out_ep, in_ep, str_idx); + +- **bFirstInterface** Indicates the offset of the first interface of this CDC ACM in all interfaces +- **int_ep** Indicates interrupt endpoint address (with direction) +- **out_ep** Indicates bulk out endpoint address (with direction) +- **in_ep** Indicates bulk in endpoint address (with direction) +- **str_idx** String ID corresponding to control interface + +HID +----------------- + +usbd_hid_init_intf +"""""""""""""""""""""""""""""""""""" + +``usbd_hid_init_intf`` is used to initialize USB HID class interface and implement related functions for this interface: + +- ``hid_class_interface_request_handler`` is used to handle USB HID class Setup requests. +- ``hid_notify_handler`` is used to handle other USB HID interrupt callback functions. + +.. code-block:: C + + struct usbd_interface *usbd_hid_init_intf(uint8_t busid, struct usbd_interface *intf, const uint8_t *desc, uint32_t desc_len); + +- **busid** USB bus ID +- **desc** Report descriptor +- **desc_len** Report descriptor length + +MSC +----------------- + +usbd_msc_init_intf +"""""""""""""""""""""""""""""""""""" +``usbd_msc_init_intf`` is used to initialize MSC class interface, implement related functions for this interface, and register endpoint callback functions. (Since MSC BOT protocol is fixed, user implementation is not needed, so endpoint callback functions naturally don't need user implementation). + +- ``msc_storage_class_interface_request_handler`` is used to handle USB MSC Setup interrupt requests. +- ``msc_storage_notify_handler`` is used to implement other USB MSC interrupt callback functions. + +- ``mass_storage_bulk_out`` is used to handle USB MSC endpoint out interrupts. +- ``mass_storage_bulk_in`` is used to handle USB MSC endpoint in interrupts. + +.. code-block:: C + + struct usbd_interface *usbd_msc_init_intf(uint8_t busid, struct usbd_interface *intf, const uint8_t out_ep, const uint8_t in_ep); + +- **busid** USB bus ID +- **out_ep** out endpoint address +- **in_ep** in endpoint address + +usbd_msc_get_cap +"""""""""""""""""""""""""""""""""""" + +``usbd_msc_get_cap`` is used to get the LUN, number of sectors, and sector size of the storage device. Users must implement this function. + +.. code-block:: C + + void usbd_msc_get_cap(uint8_t busid, uint8_t lun, uint32_t *block_num, uint16_t *block_size); + +- **busid** USB bus ID +- **lun** Storage logical unit, currently unused, defaults to supporting one +- **block_num** Number of storage sectors +- **block_size** Storage sector size + +usbd_msc_sector_read +"""""""""""""""""""""""""""""""""""" + +``usbd_msc_sector_read`` is used to read data from a storage device starting at a specific sector address. Users must implement this function. + +.. code-block:: C + + int usbd_msc_sector_read(uint8_t busid, uint8_t lun, uint32_t sector, uint8_t *buffer, uint32_t length); + +- **busid** USB bus ID +- **lun** Storage logical unit, currently unused, defaults to supporting one +- **sector** Sector offset +- **buffer** Pointer to store read data +- **length** Read length + + +usbd_msc_sector_write +"""""""""""""""""""""""""""""""""""" + +``usbd_msc_sector_write`` is used to write data to a storage device starting at a specific sector. Users must implement this function. + +.. code-block:: C + + int usbd_msc_sector_write(uint8_t busid, uint8_t lun, uint32_t sector, uint8_t *buffer, uint32_t length); + +- **busid** USB bus ID +- **lun** Storage logical unit, currently unused, defaults to supporting one +- **sector** Sector offset +- **buffer** Write data pointer +- **length** Write length + +UAC +----------------- + +usbd_audio_init_intf +"""""""""""""""""""""""""""""""""""" + +``usbd_audio_init_intf`` is used to initialize USB Audio class interface and implement related functions for this interface: + +- ``audio_class_interface_request_handler`` is used to handle USB Audio Setup interface recipient interrupt requests. +- ``audio_class_endpoint_request_handler`` is used to handle USB Audio Setup endpoint recipient interrupt requests. +- ``audio_notify_handler`` is used to implement other USB Audio interrupt callback functions. + +.. code-block:: C + + struct usbd_interface *usbd_audio_init_intf(uint8_t busid, struct usbd_interface *intf, + uint16_t uac_version, + struct audio_entity_info *table, + uint8_t num); + +- **busid** USB bus ID +- **intf** Interface handle +- **uac_version** Audio class version, UAC1.0 or UAC2.0 +- **table** Audio entity information table +- **num** Audio entity information table length + +usbd_audio_open +"""""""""""""""""""""""""""""""""""" + +``usbd_audio_open`` is used to start audio data transmission. Host sends start command callback function. + +.. code-block:: C + + void usbd_audio_open(uint8_t intf); + +- **intf** Interface number to open + +usbd_audio_close +"""""""""""""""""""""""""""""""""""" + +``usbd_audio_close`` is used to stop audio data transmission. Host sends stop command callback function. + +.. code-block:: C + + void usbd_audio_close(uint8_t intf); + +- **intf** Interface number to close + +usbd_audio_set_mute +"""""""""""""""""""""""""""""""""""" + +``usbd_audio_set_mute`` is used to set mute. + +.. code-block:: C + + void usbd_audio_set_mute(uint8_t busid, uint8_t ep, uint8_t ch, bool mute); + +- **busid** USB bus ID +- **ep** Endpoint to set mute +- **ch** Channel to set mute +- **mute** 1 means mute, 0 means opposite + +usbd_audio_set_volume +"""""""""""""""""""""""""""""""""""" + +``usbd_audio_set_volume`` is used to set volume. + +.. code-block:: C + + void usbd_audio_set_volume(uint8_t busid, uint8_t ep, uint8_t ch, int volume_db); + +- **busid** USB bus ID +- **ep** Endpoint to set volume +- **ch** Channel to set volume +- **volume_db** Volume to set in decibels, range -100dB ~ 0dB + +usbd_audio_set_sampling_freq +"""""""""""""""""""""""""""""""""""" + +``usbd_audio_set_sampling_freq`` is used to set the sampling rate of the audio module on the device + +.. code-block:: C + + void usbd_audio_set_sampling_freq(uint8_t busid, uint8_t ep, uint32_t sampling_freq); + +- **ep** Endpoint to set sampling rate +- **sampling_freq** Sampling rate to set + +usbd_audio_get_sampling_freq_table +"""""""""""""""""""""""""""""""""""" + +``usbd_audio_get_sampling_freq_table`` is used to get the list of supported sampling rates. If the function is not implemented, the default sampling rate list is used. UAC2 only. + +.. code-block:: C + + void usbd_audio_get_sampling_freq_table(uint8_t busid, uint8_t ep, uint8_t **sampling_freq_table); + +- **ep** Endpoint to get sampling rate +- **sampling_freq_table** Sampling rate list address, format refers to default sampling rate list + +UVC +----------------- + +usbd_video_init_intf +"""""""""""""""""""""""""""""""""""" + +``usbd_video_init_intf`` is used to initialize USB Video class interface and implement related functions for this interface: + +- ``video_class_interface_request_handler`` is used to handle USB Video Setup interrupt requests. +- ``video_notify_handler`` is used to implement other USB Video interrupt callback functions. + +.. code-block:: C + + struct usbd_interface *usbd_video_init_intf(uint8_t busid, struct usbd_interface *intf, + uint32_t dwFrameInterval, + uint32_t dwMaxVideoFrameSize, + uint32_t dwMaxPayloadTransferSize); +- **busid** USB bus ID +- **intf** Interface handle +- **dwFrameInterval** Video frame interval, unit 100ns +- **dwMaxVideoFrameSize** Maximum video frame size +- **dwMaxPayloadTransferSize** Maximum payload transfer size + +usbd_video_open +"""""""""""""""""""""""""""""""""""" + +``usbd_video_open`` is used to start video data transmission. + +.. code-block:: C + + void usbd_video_open(uint8_t intf); + +- **intf** Interface number to open + +usbd_video_close +"""""""""""""""""""""""""""""""""""" + +``usbd_video_close`` is used to stop video data transmission. + +.. code-block:: C + + void usbd_video_open(uint8_t intf); + +- **intf** Interface number to close + +usbd_video_stream_start_write +"""""""""""""""""""""""""""""""""""" + +``usbd_video_stream_start_write`` is used to start sending one frame of video data stream. Must be used together with `usbd_video_stream_split_transfer`. + +.. code-block:: C + + int usbd_video_stream_start_write(uint8_t busid, uint8_t ep, uint8_t *ep_buf, uint8_t *stream_buf, uint32_t stream_len, bool do_copy); + +- **busid** USB bus ID +- **ep** Video data endpoint address +- **ep_buf** Video data endpoint transfer buffer +- **stream_buf** One frame video data source buffer +- **stream_len** One frame video data source buffer size +- **do_copy** Whether to copy stream_buf data to ep_buf. This parameter is false only when stream_buf is in nocache area and DCACHE_ENABLE is not enabled + +usbd_video_stream_split_transfer +"""""""""""""""""""""""""""""""""""" + +``usbd_video_stream_split_transfer`` is used to split video data stream transmission. Must be used together with `usbd_video_stream_start_write`. + +.. code-block:: C + + int usbd_video_stream_split_transfer(uint8_t busid, uint8_t ep); + +- **busid** USB bus ID +- **ep** Video data endpoint address +- **return** Returns true when one frame data transmission is complete, false when data transmission is not complete + +RNDIS +----------------- + +CDC ECM +----------------- + +MTP +----------------- diff --git a/docs/en/api/api_host.rst b/docs/en/api/api_host.rst new file mode 100755 index 00000000..7499d188 --- /dev/null +++ b/docs/en/api/api_host.rst @@ -0,0 +1,317 @@ +Host Protocol Stack +======================================= + +For the naming, classification, and member composition of structures in the host protocol stack, refer to the following two diagrams: + +.. figure:: img/api_host1.png +.. figure:: img/api_host2.png + +CORE +----------------- + +CLASS Driver Information Structure +"""""""""""""""""""""""""""""""""""" + +.. code-block:: C + + struct usbh_class_info { + uint8_t match_flags; /* Used for product specific matches; range is inclusive */ + uint8_t bInterfaceClass; /* Base device class code */ + uint8_t bInterfaceSubClass; /* Sub-class, depends on base class. Eg. */ + uint8_t bInterfaceProtocol; /* Protocol, depends on base class. Eg. */ + const uint16_t (*id_table)[2]; /* List of Vendor/Product ID pairs */ + const struct usbh_class_driver *class_driver; + }; + +Endpoint Structure +"""""""""""""""""""""""""""""""""""" + +.. code-block:: C + + struct usbh_endpoint { + struct usb_endpoint_descriptor ep_desc; + }; + +Interface Altsetting Structure +"""""""""""""""""""""""""""""""""""" + +.. code-block:: C + + struct usbh_interface_altsetting { + struct usb_interface_descriptor intf_desc; + struct usbh_endpoint ep[CONFIG_USBHOST_MAX_ENDPOINTS]; + }; + +Interface Structure +"""""""""""""""""""""""""""""""""""" + +.. code-block:: C + + struct usbh_interface { + char devname[CONFIG_USBHOST_DEV_NAMELEN]; + struct usbh_class_driver *class_driver; + void *priv; + struct usbh_interface_altsetting altsetting[CONFIG_USBHOST_MAX_INTF_ALTSETTINGS]; + uint8_t altsetting_num; + }; + +Configuration Structure +"""""""""""""""""""""""""""""""""""" + +.. code-block:: C + + struct usbh_configuration { + struct usb_configuration_descriptor config_desc; + struct usbh_interface intf[CONFIG_USBHOST_MAX_INTERFACES]; + }; + +hubport Structure +"""""""""""""""""""""""""""""""""""" + +.. code-block:: C + + struct usbh_hubport { + bool connected; /* True: device connected; false: disconnected */ + uint8_t port; /* Hub port index */ + uint8_t dev_addr; /* device address */ + uint8_t speed; /* device speed */ + uint8_t depth; /* distance from root hub */ + uint8_t route; /* route string */ + uint8_t slot_id; /* slot id */ + struct usb_device_descriptor device_desc; + struct usbh_configuration config; + const char *iManufacturer; + const char *iProduct; + const char *iSerialNumber; + uint8_t *raw_config_desc; + struct usb_setup_packet *setup; + struct usbh_hub *parent; + struct usbh_hub *self; /* if this hubport is a hub */ + struct usbh_bus *bus; + struct usb_endpoint_descriptor ep0; + struct usbh_urb ep0_urb; + usb_osal_mutex_t mutex; + }; + +hub Structure +"""""""""""""""""""""""""""""""""""" + +.. code-block:: C + + struct usbh_hub { + bool connected; + bool is_roothub; + uint8_t index; + uint8_t hub_addr; + uint8_t speed; + uint8_t nports; + uint8_t powerdelay; + uint8_t tt_think; + bool ismtt; + struct usb_hub_descriptor hub_desc; /* USB 2.0 only */ + struct usb_hub_ss_descriptor hub_ss_desc; /* USB 3.0 only */ + struct usbh_hubport child[CONFIG_USBHOST_MAX_EHPORTS]; + struct usbh_hubport *parent; + struct usbh_bus *bus; + struct usb_endpoint_descriptor *intin; + struct usbh_urb intin_urb; + uint8_t *int_buffer; + struct usb_osal_timer *int_timer; + }; + +usbh_initialize +"""""""""""""""""""""""""""""""""""" + +``usbh_initialize`` is used to initialize the USB host protocol stack, including: initializing the USB host controller, creating roothub device, creating hub detection thread. + +.. code-block:: C + + int usbh_initialize(uint8_t busid, uint32_t reg_base, usbh_event_handler_t event_handler); + +- **busid** bus id, starting from 0, cannot exceed `CONFIG_USBHOST_MAX_BUS` +- **reg_base** hcd register base address +- **event_handler** host event callback function, can be NULL +- **return** 0 indicates normal, other values indicate error + +usbh_find_class_instance +"""""""""""""""""""""""""""""""""""" + +``usbh_find_class_instance`` finds the corresponding class structure handle based on the registered class name. + +.. code-block:: C + + void *usbh_find_class_instance(const char *devname); + +- **devname** class name +- **return** class structure handle + +lsusb +"""""""""""""""""""""""""""""""""""" + +``lsusb`` is used to view and operate device information on the hub. Requires shell plugin to use. + +.. code-block:: C + + int lsusb(int argc, char **argv); + +SERIAL +----------------- + +usbh_serial_open +"""""""""""""""""""""""""""""""""""" + +``usbh_serial_open`` opens a serial device according to the path. + +.. code-block:: C + + struct usbh_serial *usbh_serial_open(const char *devname, uint32_t open_flags); + +- **devname** serial path +- **open_flags** open flags, refer to `USBH_SERIAL_OFLAG_*` definitions +- **return** serial structure handle + +usbh_serial_close +"""""""""""""""""""""""""""""""""""" + +``usbh_serial_close`` closes the serial device. + +.. code-block:: C + + void usbh_serial_close(struct usbh_serial *serial); + +- **serial** serial structure handle + +usbh_serial_control +"""""""""""""""""""""""""""""""""""" + +``usbh_serial_control`` configures the serial port. + +.. code-block:: C + + int usbh_serial_control(struct usbh_serial *serial, int cmd, void *arg); + +- **serial** serial structure handle +- **cmd** control command, refer to `USBH_SERIAL_CMD_*` definitions +- **arg** control parameter pointer +- **return** 0 indicates normal, other values indicate error + +usbh_serial_write +"""""""""""""""""""""""""""""""""""" + +``usbh_serial_write`` writes data to the serial port. + +.. code-block:: C + + int usbh_serial_write(struct usbh_serial *serial, const void *buffer, uint32_t buflen); + +- **serial** serial structure handle +- **buffer** data buffer pointer +- **buflen** length of data to write +- **return** actual length of data written or error code + +.. note:: If CONFIG_USB_DCACHE_ENABLE is not enabled, buffer needs to be in nocache area, otherwise it needs to be aligned to CONFIG_USB_ALIGN_SIZE area. + +usbh_serial_read +"""""""""""""""""""""""""""""""""""" + +``usbh_serial_read`` reads data from the serial port. **If baud rate is not set, this API is not allowed to be used. After setting baud rate, rx reception will be enabled internally and data will be written to ringbuf**. + +.. code-block:: C + + int usbh_serial_read(struct usbh_serial *serial, void *buffer, uint32_t buflen); + +- **serial** serial structure handle +- **buffer** data buffer pointer +- **buflen** maximum length of data to read +- **return** actual length of data read or error code + +.. note:: Since ringbuffer is used internally, there are no restrictions on user buffer attributes. + +usbh_serial_cdc_write_async +"""""""""""""""""""""""""""""""""""" + +``usbh_serial_cdc_write_async`` asynchronously writes data to the serial port. **If baud rate is set, this API is not allowed to be used**. + +.. code-block:: C + + int usbh_serial_cdc_write_async(struct usbh_serial *serial, uint8_t *buffer, uint32_t buflen, usbh_complete_callback_t complete, void *arg); + +- **serial** serial structure handle +- **buffer** data buffer pointer +- **buflen** length of data to send +- **complete** data write completion callback function +- **arg** callback function parameter +- **return** 0 indicates normal, other values indicate error + +.. note:: If CONFIG_USB_DCACHE_ENABLE is not enabled, buffer needs to be in nocache area, otherwise it needs to be aligned to CONFIG_USB_ALIGN_SIZE area. + +usbh_serial_cdc_read_async +"""""""""""""""""""""""""""""""""""" + +``usbh_serial_cdc_read_async`` asynchronously reads data from the serial port. **If baud rate is set, this API is not allowed to be used. After setting baud rate, rx reception will be enabled internally and data will be written to ringbuf**. + +.. code-block:: C + + int usbh_serial_cdc_read_async(struct usbh_serial *serial, uint8_t *buffer, uint32_t buflen, usbh_complete_callback_t complete, void *arg); + +- **serial** serial structure handle +- **buffer** data buffer pointer +- **buflen** maximum length of data to read, up to 16K at a time. Must be a multiple of wMaxPacketSize +- **complete** data read completion callback function +- **arg** callback function parameter +- **return** 0 indicates normal, other values indicate error + +.. note:: If CONFIG_USB_DCACHE_ENABLE is not enabled, buffer needs to be in nocache area, otherwise it needs to be aligned to CONFIG_USB_ALIGN_SIZE area. + +HID +----------------- + +MSC +----------------- + +usbh_msc_scsi_init +"""""""""""""""""""""""""""""""""""" + +``usbh_msc_scsi_init`` initializes msc scsi device. Gets MSC status and capacity information. + +.. code-block:: C + + int usbh_msc_scsi_init(struct usbh_msc *msc_class); + +- **msc_class** msc structure handle +- **return** 0 indicates normal, other values indicate error + +usbh_msc_scsi_write10 +"""""""""""""""""""""""""""""""""""" + +``usbh_msc_scsi_write10`` writes data to msc device. + +.. code-block:: C + + int usbh_msc_scsi_write10(struct usbh_msc *msc_class, uint32_t start_sector, const uint8_t *buffer, uint32_t nsectors); + +- **msc_class** msc structure handle +- **start_sector** starting sector +- **buffer** data buffer pointer +- **nsectors** number of sectors to write +- **return** returns 0 for normal, other values indicate error + +usbh_msc_scsi_read10 +"""""""""""""""""""""""""""""""""""" + +``usbh_msc_scsi_read10`` reads data from msc device. + +.. code-block:: C + + int usbh_msc_scsi_read10(struct usbh_msc *msc_class, uint32_t start_sector, uint8_t *buffer, uint32_t nsectors); + +- **msc_class** msc structure handle +- **start_sector** starting sector +- **buffer** data buffer pointer +- **nsectors** number of sectors to read +- **return** returns 0 for normal, other values indicate error + +NETWORK +----------------- + +Already integrated with lwIP protocol stack or other network protocol stacks, use socket API. \ No newline at end of file diff --git a/docs/en/api/api_port.rst b/docs/en/api/api_port.rst new file mode 100755 index 00000000..9f5fe5c1 --- /dev/null +++ b/docs/en/api/api_port.rst @@ -0,0 +1,266 @@ +Host and Device Drivers +======================================= + +.. note:: Please note that starting from version v1.1, the busid parameter has been added, while everything else remains unchanged, so API documentation is not updated + +device controller(dcd) +------------------------- + +usb_dc_init +"""""""""""""""""""""""""""""""""""" + +``usb_dc_init`` is used to initialize USB device controller registers, set USB pins, clock, interrupts, etc. **This function is not open to users**. + +.. code-block:: C + + int usb_dc_init(void); + +- **return** Returns 0 for success, other values indicate error + +usb_dc_deinit +"""""""""""""""""""""""""""""""""""" + +``usb_dc_deinit`` is used to de-initialize USB device controller registers. **This function is not open to users**. + +.. code-block:: C + + int usb_dc_deinit(void); + +- **return** Returns 0 for success, other values indicate error + +usbd_set_address +"""""""""""""""""""""""""""""""""""" + +``usbd_set_address`` sets the device address. **This function is not open to users**. + +.. code-block:: C + + int usbd_set_address(const uint8_t addr); + +- **addr** Device address +- **return** Returns 0 for success, other values indicate error + +usbd_ep_open +"""""""""""""""""""""""""""""""""""" + +``usbd_ep_open`` sets endpoint properties and enables corresponding endpoint interrupts. **This function is not open to users**. + +.. code-block:: C + + int usbd_ep_open(const struct usb_endpoint_descriptor *ep); + +- **ep** Endpoint descriptor +- **return** Returns 0 for success, other values indicate error + +usbd_ep_close +"""""""""""""""""""""""""""""""""""" + +``usbd_ep_close`` closes an endpoint. **This function is not open to users**. + +.. code-block:: C + + int usbd_ep_close(const uint8_t ep); + +- **ep** Endpoint address +- **return** Returns 0 for success, other values indicate error + +usbd_ep_set_stall +"""""""""""""""""""""""""""""""""""" + +``usbd_ep_set_stall`` sets an endpoint to stall state and sends a stall handshake packet. **This function is open to users**. + +.. code-block:: C + + int usbd_ep_set_stall(const uint8_t ep); + +- **ep** Endpoint address +- **return** Returns 0 for success, other values indicate error + +usbd_ep_clear_stall +"""""""""""""""""""""""""""""""""""" + +``usbd_ep_clear_stall`` clears the stall state of an endpoint. **This function is not open to users**. + +.. code-block:: C + + int usbd_ep_clear_stall(const uint8_t ep); + +- **ep** Endpoint address +- **return** Returns 0 for success, other values indicate error + +usbd_ep_is_stalled +"""""""""""""""""""""""""""""""""""" + +``usbd_ep_is_stalled`` reads the current stall state of an endpoint. **This function is not open to users**. + +.. code-block:: C + + int usbd_ep_is_stalled(const uint8_t ep, uint8_t *stalled); + +- **ep** Endpoint address +- **return** Returns 1 for stalled, 0 for not stalled + +usbd_ep_start_write +"""""""""""""""""""""""""""""""""""" + +``usbd_ep_start_write`` starts endpoint transmission. After transmission completion, it will call the registered IN endpoint transfer completion interrupt callback function. This function performs asynchronous transmission. **This function is open to users**. + +.. code-block:: C + + int usbd_ep_start_write(const uint8_t ep, const uint8_t *data, uint32_t data_len); + +- **ep** IN endpoint address +- **data** Transmission data buffer +- **data_len** Transmission length, theoretically unlimited, recommended within 16K bytes +- **return** Returns 0 for success, other values indicate error + +usbd_ep_start_read +"""""""""""""""""""""""""""""""""""" + +``usbd_ep_start_read`` starts endpoint reception. After reception completion, it will call the registered OUT endpoint transfer completion interrupt callback function. This function performs asynchronous reception. **This function is open to users**. + +.. code-block:: C + + int usbd_ep_start_read(const uint8_t ep, uint8_t *data, uint32_t data_len); + +- **ep** OUT endpoint address +- **data** Reception data buffer +- **data_len** Reception length, theoretically unlimited, recommended within 16K bytes, and preferably a multiple of maximum packet size +- **return** Returns 0 for success, other values indicate error + +.. note:: After starting reception, transfer completion interrupt will be triggered under two conditions: 1. Last packet is a short packet (less than EP MPS); 2. Total received length equals data_len + +.. note:: For bulk transfers, data_len is usually designed as EP MPS. The following three cases can be modified to multiple EP MPS: fixed length; custom protocol with length information (MSC); host manually sends ZLP or short packet (RNDIS) + +host controller(hcd) +------------------------ + +usb_hc_init +"""""""""""""""""""""""""""""""""""" + +``usb_hc_init`` is used to initialize USB host controller registers, set USB pins, clock, interrupts, etc. **This function is not open to users**. + +.. code-block:: C + + int usb_hc_init(void); + +- **return** Returns 0 for success, other values indicate error + +usb_hc_deinit +"""""""""""""""""""""""""""""""""""" + +``usb_hc_deinit`` is used to de-initialize USB host controller registers. **This function is not open to users**. + +.. code-block:: C + + int usb_hc_deinit(void); + +- **return** Returns 0 for success, other values indicate error + +usbh_roothub_control +"""""""""""""""""""""""""""""""""""" + +``usbh_roothub_control`` is used to send requests to the root hub. **This function is not open to users**. + +.. code-block:: C + + int usbh_roothub_control(struct usb_setup_packet *setup, uint8_t *buf); + +- **setup** Request +- **buf** Reception buffer +- **return** Returns 0 for success, other values indicate error + +usbh_submit_urb +"""""""""""""""""""""""""""""""""""" + +``usbh_submit_urb`` performs data requests to endpoints at a specific address. **This function is open to users**. + +.. code-block:: C + + int usbh_submit_urb(struct usbh_urb *urb); + +- **urb** USB request block +- **return** Returns 0 for success, other values indicate error + +Among them, the `urb` structure information is as follows: + +.. code-block:: C + + struct usbh_urb { + usb_slist_t list; + void *hcpriv; + struct usbh_hubport *hport; + struct usb_endpoint_descriptor *ep; + uint8_t data_toggle; + uint8_t interval; + struct usb_setup_packet *setup; + uint8_t *transfer_buffer; + uint32_t transfer_buffer_length; + int transfer_flags; + uint32_t actual_length; + uint32_t timeout; + int errorcode; + uint32_t num_of_iso_packets; + uint32_t start_frame; + usbh_complete_callback_t complete; + void *arg; + #if defined(__ICCARM__) || defined(__ICCRISCV__) || defined(__ICCRX__) + struct usbh_iso_frame_packet *iso_packet; + #else + struct usbh_iso_frame_packet iso_packet[0]; + #endif + }; + +- **hcpriv** Host controller driver private member +- **hport** The hport used by current URB +- **ep** The endpoint used by current URB +- **data_toggle** Current data toggle +- **interval** URB transfer interval in microseconds. If interval is greater than 1000us, software timer needs to be used for maintenance +- **setup** Setup request buffer, used by endpoint 0 +- **transfer_buffer** Transfer data buffer +- **transfer_buffer_length** Transfer length +- **transfer_flags** Flags carried during transfer +- **actual_length** Actual transfer length +- **timeout** Transfer timeout. If 0, the function is non-blocking and can be used in interrupts +- **errorcode** Error code +- **num_of_iso_packets** Number of ISO frames or microframes +- **complete** Transfer completion callback function +- **arg** Parameters carried when transfer completes +- **iso_packet** ISO data packet + +.. note:: If there are no special time requirements for timeout, it must be set to 0xffffffff. In principle, timeout is not allowed. If timeout occurs, generally cannot continue working + +`errorcode` can return the following values: + +.. code-block:: C + + #define USB_ERR_NOMEM 1 + #define USB_ERR_INVAL 2 + #define USB_ERR_NODEV 3 + #define USB_ERR_NOTCONN 4 + #define USB_ERR_NOTSUPP 5 + #define USB_ERR_BUSY 6 + #define USB_ERR_RANGE 7 + #define USB_ERR_STALL 8 + #define USB_ERR_BABBLE 9 + #define USB_ERR_NAK 10 + #define USB_ERR_DT 11 + #define USB_ERR_IO 12 + #define USB_ERR_SHUTDOWN 13 + #define USB_ERR_TIMEOUT 14 + +Among them, the `iso_packet` structure information is as follows: + +.. code-block:: C + + struct usbh_iso_frame_packet { + uint8_t *transfer_buffer; + uint32_t transfer_buffer_length; + uint32_t actual_length; + int errorcode; + }; + +- **transfer_buffer** Transfer data buffer +- **transfer_buffer_length** Transfer length +- **actual_length** Actual transfer length +- **errorcode** Error code \ No newline at end of file diff --git a/docs/en/api/img/api_device1.png b/docs/en/api/img/api_device1.png new file mode 100755 index 00000000..ba218b65 Binary files /dev/null and b/docs/en/api/img/api_device1.png differ diff --git a/docs/en/api/img/api_host1.png b/docs/en/api/img/api_host1.png new file mode 100755 index 00000000..82932f50 Binary files /dev/null and b/docs/en/api/img/api_host1.png differ diff --git a/docs/en/api/img/api_host2.png b/docs/en/api/img/api_host2.png new file mode 100755 index 00000000..7f6d60b8 Binary files /dev/null and b/docs/en/api/img/api_host2.png differ diff --git a/docs/en/class/class_audio.rst b/docs/en/class/class_audio.rst new file mode 100755 index 00000000..c706afd5 --- /dev/null +++ b/docs/en/class/class_audio.rst @@ -0,0 +1,4 @@ +UAC +======================================= + +Reference official audio-related PDFs \ No newline at end of file diff --git a/docs/en/class/class_cdc.rst b/docs/en/class/class_cdc.rst new file mode 100755 index 00000000..23826066 --- /dev/null +++ b/docs/en/class/class_cdc.rst @@ -0,0 +1,4 @@ +CDC +======================================= + +Reference official CDC-related PDFs \ No newline at end of file diff --git a/docs/en/class/class_hid.rst b/docs/en/class/class_hid.rst new file mode 100755 index 00000000..14253a9f --- /dev/null +++ b/docs/en/class/class_hid.rst @@ -0,0 +1,4 @@ +HID +======================================= + +Reference official HID-related PDFs \ No newline at end of file diff --git a/docs/en/class/class_msc.rst b/docs/en/class/class_msc.rst new file mode 100755 index 00000000..6eb14313 --- /dev/null +++ b/docs/en/class/class_msc.rst @@ -0,0 +1,4 @@ +MSC +======================================= + +Reference official MSC-related PDFs \ No newline at end of file diff --git a/docs/en/class/class_video.rst b/docs/en/class/class_video.rst new file mode 100755 index 00000000..a93c2fa2 --- /dev/null +++ b/docs/en/class/class_video.rst @@ -0,0 +1,4 @@ +UVC +======================================= + +Reference official video-related PDFs \ No newline at end of file diff --git a/docs/en/class/winusb.rst b/docs/en/class/winusb.rst new file mode 100755 index 00000000..11041c5c --- /dev/null +++ b/docs/en/class/winusb.rst @@ -0,0 +1,2 @@ +WINUSB +======================================= \ No newline at end of file diff --git a/docs/en/conf.py b/docs/en/conf.py new file mode 100755 index 00000000..22427158 --- /dev/null +++ b/docs/en/conf.py @@ -0,0 +1,37 @@ +# Configuration file for the Sphinx documentation builder. + +# -- Project information + +project = 'CherryUSB' +copyright = '2022 ~ 2026, sakumisu' +author = 'sakumisu' + +release = '1.6.0' +version = '1.6.0' + +# -- General configuration + +extensions = [ + 'sphinx.ext.duration', + 'sphinx.ext.doctest', + 'sphinx.ext.autodoc', + 'sphinx.ext.autosummary', + 'sphinx.ext.intersphinx', + 'recommonmark', + 'sphinx_markdown_tables' +] + +intersphinx_mapping = { +# 'python': ('https://docs.python.org/3/', None), +# 'sphinx': ('https://www.sphinx-doc.org/en/master/', None), +} +intersphinx_disabled_domains = ['std'] + +templates_path = ['_templates'] + +# -- Options for HTML output + +html_theme = 'sphinx_rtd_theme' + +# -- Options for EPUB output +epub_show_urls = 'footnote' diff --git a/docs/en/demo/img/cherryadb.png b/docs/en/demo/img/cherryadb.png new file mode 100755 index 00000000..512586b9 Binary files /dev/null and b/docs/en/demo/img/cherryadb.png differ diff --git a/docs/en/demo/img/otg.png b/docs/en/demo/img/otg.png new file mode 100755 index 00000000..9605176a Binary files /dev/null and b/docs/en/demo/img/otg.png differ diff --git a/docs/en/demo/img/rtt_adb_shell1.png b/docs/en/demo/img/rtt_adb_shell1.png new file mode 100755 index 00000000..df4964a2 Binary files /dev/null and b/docs/en/demo/img/rtt_adb_shell1.png differ diff --git a/docs/en/demo/img/rtt_adb_shell2.png b/docs/en/demo/img/rtt_adb_shell2.png new file mode 100755 index 00000000..88d99a6a Binary files /dev/null and b/docs/en/demo/img/rtt_adb_shell2.png differ diff --git a/docs/en/demo/img/usbh_serial.png b/docs/en/demo/img/usbh_serial.png new file mode 100755 index 00000000..da929c4a Binary files /dev/null and b/docs/en/demo/img/usbh_serial.png differ diff --git a/docs/en/demo/usb_otg.rst b/docs/en/demo/usb_otg.rst new file mode 100755 index 00000000..3d206ec5 --- /dev/null +++ b/docs/en/demo/usb_otg.rst @@ -0,0 +1,14 @@ +USB OTG +================= + +If you need to use OTG functionality, first the chip you're using needs to support ID detection capability, then enable the ``CONFIG_USB_OTG_ENABLE`` macro, and replace ``usbh_initialize`` or ``usbd_initialize`` in previous examples with ``usbotg_initialize``. + +The ID detection circuit varies depending on different USB interface types, with micro-USB and USB-C being the two common interface types. + +- If it's a micro-USB interface, connect the ID line to the chip's ID pin and enable the ID function. +- If it's a USB-C interface, since there's no ID pin, you need to use CC circuit to convert to ID and then connect to the chip's ID pin. A common circuit diagram is shown below (DNP means Do Not Populate): + +.. figure:: img/otg.png + + +.. note:: In addition to the ID pin, you also need to add VBUS output switch control. When working in host mode, enable VBUS power supply; when working in device mode, disable VBUS power supply. \ No newline at end of file diff --git a/docs/en/demo/usbd_adb.rst b/docs/en/demo/usbd_adb.rst new file mode 100755 index 00000000..e11e784d --- /dev/null +++ b/docs/en/demo/usbd_adb.rst @@ -0,0 +1,28 @@ +ADB Device +================= + +The adb device demo refers to the `demo/adb/usbd_adb_template.c` template. It adapts to **cherrysh** (`platform/demo/adb/cherrysh_port.c`) and **rt-thread msh** (`platform/rtthread/usbd_adb_shell.c`) by default. You only need to add the following initialization in main. + +.. code-block:: C + + cherryadb_init(0, xxxxx); + +If using rt-thread, you also need to enable adb device in menuconfig. + +.. figure:: img/rtt_adb_shell1.png + +Entering ADB +-------------- + +- When using **cherrysh**, automatically enters adb mode after enumeration is completed +- When using **msh**, you need to input ``adb_enter`` in **msh** to enter adb mode + +Exiting ADB +-------------- + +- When using **cherrysh**, input ``exit`` to exit adb mode +- When using **msh**, you need to input ``adb_exit`` in **msh** to exit adb mode + +.. figure:: img/cherryadb.png + +.. figure:: img/rtt_adb_shell2.png diff --git a/docs/en/demo/usbd_audiov1.rst b/docs/en/demo/usbd_audiov1.rst new file mode 100755 index 00000000..5bf0629c --- /dev/null +++ b/docs/en/demo/usbd_audiov1.rst @@ -0,0 +1,10 @@ +AudioV1 Device +================= + +UAC1 demo refers to `demo/audio_v1_*.c` template. + +When using UAC1.0, pay attention to the following points: + +- When using Windows, when modifying any descriptor parameters, you must synchronously modify the string descriptor and uninstall the driver, otherwise Windows will consider the device unchanged and continue to use the old driver, causing device recognition failure. Linux is not subject to this restriction. +- Download RemoveGhostDev64.exe from the QQ group files to automatically delete all USB registered driver information, eliminating the need for the first step +- Prohibit adding print statements and time-consuming operations in interrupts, otherwise it will affect USB transmission according to interval \ No newline at end of file diff --git a/docs/en/demo/usbd_audiov2.rst b/docs/en/demo/usbd_audiov2.rst new file mode 100755 index 00000000..8a66d10f --- /dev/null +++ b/docs/en/demo/usbd_audiov2.rst @@ -0,0 +1,10 @@ +AudioV2 Device +================= + +When using UAC2.0, please note the following points: + +- On Windows, when modifying any parameter in the descriptor, the string descriptor must be modified synchronously and the driver must be uninstalled. Otherwise, Windows will think the device has not changed and continue to use the old driver, resulting in device recognition failure. Linux is not subject to this limitation. +- You can download RemoveGhostDev64.exe from the QQ group files to automatically delete all USB registered driver information, eliminating the need for the first step +- Windows 10 UAC2.0 functionality is incomplete, please use Windows 11 to test UAC2.0 functionality. Linux is not subject to this limitation +- Windows has calculation errors in the sampling rate range setting for multi-channel (more than 2 channels). For example, if you set 8K~96K, the actual range is greater than or equal to 8K and less than 96K, not less than or equal to 96K. Linux is not subject to this limitation +- Prohibit adding prints and time-consuming operations in interrupts, otherwise it will affect USB transmission according to interval \ No newline at end of file diff --git a/docs/en/demo/usbd_cdc_acm.rst b/docs/en/demo/usbd_cdc_acm.rst new file mode 100755 index 00000000..28d9affa --- /dev/null +++ b/docs/en/demo/usbd_cdc_acm.rst @@ -0,0 +1,104 @@ +CDC ACM Device +================= + +This demo mainly demonstrates CDC ACM functionality. Reference the `demo/cdc_acm_template.c` template. Includes transmission/reception testing, DTR control, ZLP testing, and performance testing. + +- Allocate read/write buffers for data transmission/reception. Buffers need to be modified with nocache. Here we use 2048 bytes for both read and write for subsequent ZLP testing and performance testing. + +.. code-block:: C + + USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t read_buffer[2048]; /* 2048 is only for test speed , please use CDC_MAX_MPS for common*/ + USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t write_buffer[2048]; + + +- In the protocol stack event callback, we need to start the first transmission after enumeration is complete and clear the related flags. This can be done in the reset event or in the configured event. + +.. code-block:: C + + static void usbd_event_handler(uint8_t busid, uint8_t event) + { + switch (event) { + case USBD_EVENT_RESET: + break; + case USBD_EVENT_CONNECTED: + break; + case USBD_EVENT_DISCONNECTED: + break; + case USBD_EVENT_RESUME: + break; + case USBD_EVENT_SUSPEND: + break; + case USBD_EVENT_CONFIGURED: + ep_tx_busy_flag = false; + /* setup first out ep read transfer */ + usbd_ep_start_read(busid, CDC_OUT_EP, read_buffer, 2048); + break; + case USBD_EVENT_SET_REMOTE_WAKEUP: + break; + case USBD_EVENT_CLR_REMOTE_WAKEUP: + break; + + default: + break; + } + } + +- Continue to initiate reception in the reception complete interrupt; determine whether to send ZLP in the transmission complete interrupt. + +.. code-block:: C + + void usbd_cdc_acm_bulk_out(uint8_t busid, uint8_t ep, uint32_t nbytes) + { + USB_LOG_RAW("actual out len:%d\r\n", nbytes); + // for (int i = 0; i < 100; i++) { + // printf("%02x ", read_buffer[i]); + // } + // printf("\r\n"); + /* setup next out ep read transfer */ + usbd_ep_start_read(busid, CDC_OUT_EP, read_buffer, 2048); + } + + void usbd_cdc_acm_bulk_in(uint8_t busid, uint8_t ep, uint32_t nbytes) + { + USB_LOG_RAW("actual in len:%d\r\n", nbytes); + + if ((nbytes % usbd_get_ep_mps(busid, ep)) == 0 && nbytes) { + /* send zlp */ + usbd_ep_start_write(busid, CDC_IN_EP, NULL, 0); + } else { + ep_tx_busy_flag = false; + } + } + +- The following is for testing DTR functionality and controlling USB transmission. DTR and RTS are only used in conjunction with UART; for pure USB, they are not very useful - this is just for testing. DTR switch uses any serial port host computer and check DTR. + +.. code-block:: C + + void usbd_cdc_acm_set_dtr(uint8_t busid, uint8_t intf, bool dtr) + { + if (dtr) { + dtr_enable = 1; + } else { + dtr_enable = 0; + } + } + +- Keep calling send in the main function + +.. code-block:: C + + void cdc_acm_data_send_with_dtr_test(uint8_t busid) + { + if (dtr_enable) { + ep_tx_busy_flag = true; + usbd_ep_start_write(busid, CDC_IN_EP, write_buffer, 2048); + while (ep_tx_busy_flag) { + } + } + } + +- Note that we set the length to 2048 for testing ZLP functionality. In actual use, the receive length should use CDC_MAX_MPS. See :ref:`usb_ext` for specific reasons. +- For performance testing, use tools/test_srcipts/test_cdc_speed.py and remove the print statements in `usbd_cdc_acm_bulk_out` and `usbd_cdc_acm_bulk_in` before testing, otherwise it will affect the test results. + + +In addition, for CDC ACM with OS, we usually use asynchronous read and store data in a ringbuffer, and use synchronous write with semaphore. \ No newline at end of file diff --git a/docs/en/demo/usbd_ecm.rst b/docs/en/demo/usbd_ecm.rst new file mode 100755 index 00000000..de148621 --- /dev/null +++ b/docs/en/demo/usbd_ecm.rst @@ -0,0 +1,4 @@ +CDC ECM Device +================= + +ECM demo refers to the `demo/cdc_ecm*.c` template. By default it interfaces with lwip protocol stack, and the upper layer can use lwip api. \ No newline at end of file diff --git a/docs/en/demo/usbd_hid.rst b/docs/en/demo/usbd_hid.rst new file mode 100755 index 00000000..71147dfa --- /dev/null +++ b/docs/en/demo/usbd_hid.rst @@ -0,0 +1,4 @@ +HID Device +================= + +HID functionality is relatively simple, so no detailed explanation is needed. Note that when using the HID custom example, it needs to be used with `tools/test_srcipts/test_hid_inout.py` (with report ID functionality). \ No newline at end of file diff --git a/docs/en/demo/usbd_msc.rst b/docs/en/demo/usbd_msc.rst new file mode 100755 index 00000000..02b05add --- /dev/null +++ b/docs/en/demo/usbd_msc.rst @@ -0,0 +1,39 @@ +MSC Device +================= + +This section mainly demonstrates USB mass storage device functionality. By default, RAM is used as storage medium to simulate a USB drive. + +- Implement read/write and capacity acquisition interfaces for the USB drive. Note that the capacity block_num is virtual - there aren't actually that many blocks. Read/write data exceeding BLOCK_COUNT will be discarded. + +block_size is generally 512/2048/4096. + +.. code-block:: C + + void usbd_msc_get_cap(uint8_t busid, uint8_t lun, uint32_t *block_num, uint32_t *block_size) + { + *block_num = 1000; //Pretend having so many buffer,not has actually. + *block_size = BLOCK_SIZE; + } + int usbd_msc_sector_read(uint8_t busid, uint8_t lun, uint32_t sector, uint8_t *buffer, uint32_t length) + { + if (sector < BLOCK_COUNT) + memcpy(buffer, mass_block[sector].BlockSpace, length); + return 0; + } + + int usbd_msc_sector_write(uint8_t busid, uint8_t lun, uint32_t sector, uint8_t *buffer, uint32_t length) + { + if (sector < BLOCK_COUNT) + memcpy(mass_block[sector].BlockSpace, buffer, length); + return 0; + } + +- By default, the above APIs execute in interrupt context. If you need to execute in non-interrupt context, you can choose the following: + +1. In bare metal, enable `CONFIG_USBDEV_MSC_POLLING` and call `usbd_msc_polling` in while1, then read/write functions execute in while1. + +2. In OS, enable `CONFIG_USBDEV_MSC_THREAD`, then read/write functions execute in thread. + +- Modifying `CONFIG_USBDEV_MSC_BUFSIZE` will affect U disk read/write speed. It must be an integer multiple of block_size, of course, it will also increase RAM usage. + +- If RAM example works but doesn't work after changing medium to SD or FLASH, it must be a medium driver problem. \ No newline at end of file diff --git a/docs/en/demo/usbd_mtp.rst b/docs/en/demo/usbd_mtp.rst new file mode 100755 index 00000000..0c9bd191 --- /dev/null +++ b/docs/en/demo/usbd_mtp.rst @@ -0,0 +1,6 @@ +MTP Device +================= + +MTP demo references the `demo/mtp_template.c` template. Adapted for FatFS file system by default (`platform/fatfs/usbd_fatfs_mtp.c`). + +.. note:: MTP is commercially charged and does not provide open source MTP driver code. Please contact official support to purchase authorization. \ No newline at end of file diff --git a/docs/en/demo/usbd_rndis.rst b/docs/en/demo/usbd_rndis.rst new file mode 100755 index 00000000..623c9208 --- /dev/null +++ b/docs/en/demo/usbd_rndis.rst @@ -0,0 +1,4 @@ +CDC RNDIS Device +================= + +RNDIS demo refers to `demo/cdc_rndis*.c` template. By default it interfaces with lwip protocol stack, the upper layer can use lwip api. \ No newline at end of file diff --git a/docs/en/demo/usbd_vendor.rst b/docs/en/demo/usbd_vendor.rst new file mode 100755 index 00000000..c5a0b3c8 --- /dev/null +++ b/docs/en/demo/usbd_vendor.rst @@ -0,0 +1,44 @@ +Writing Vendor Device Driver +============================================ + +This section mainly introduces how to write a vendor device driver. + +- First copy a class/template/usbd_xxx.c file +- Implement the following three callback functions. Generally speaking, vendor drivers only need to implement vendor_handlerDevice 驱动编写 + +.. code-block:: C + + intf->class_interface_handler = xxx_class_interface_request_handler; + intf->class_endpoint_handler = NULL; + intf->vendor_handler = NULL; + intf->notify_handler = xxx_notify_handler; + +- Example as follows + +case1 demonstrates processing of host IN data, copying data to *data and specifying the length of *len. The protocol stack will automatically send to the host without requiring users to manually call send API. + +case2 demonstrates processing of host OUT data. When this function is executed, it means all data has been received and can directly read data from *data with length *len. + +.. code-block:: C + + static int xxx_vendor_request_handler(uint8_t busid, struct usb_setup_packet *setup, uint8_t **data, uint32_t *len) + { + USB_LOG_WRN("XXX Class request: " + "bRequest 0x%02x\r\n", + setup->bRequest); + + switch (setup->bRequest) { + case 1: + memcpy(*data, xxx, sizeof(xxx)); + *len = sizeof(xxx); + case 2: + hexdump(*data, *len); + default: + USB_LOG_WRN("Unhandled XXX Class bRequest 0x%02x\r\n", setup->bRequest); + return -1; + } + + return 0; + } + +- Finally register the interface using the form usbd_add_interface(busid, usbd_xxx_init_intf(&intf)) \ No newline at end of file diff --git a/docs/en/demo/usbd_video.rst b/docs/en/demo/usbd_video.rst new file mode 100755 index 00000000..548e68b7 --- /dev/null +++ b/docs/en/demo/usbd_video.rst @@ -0,0 +1,83 @@ +USB Video Device +================= + +This section mainly demonstrates USB UVC functionality, supporting YUYV, MJPEG, H264 formats. For demonstration convenience, static images are used throughout. + +The demo includes **video_static_yuyv_template**, **video_static_mjpeg_template**, **video_static_h264_template**, with only descriptors and image data being different. + +- In high-speed mode, the default maximum is 1024 bytes, but if the chip supports additional transactions, it can be configured up to 2048 bytes or 3072 bytes, which can improve transmission efficiency. + +.. code-block:: C + + #ifdef CONFIG_USB_HS + #define MAX_PAYLOAD_SIZE 1024 // for high speed with one transcations every one micro frame + #define VIDEO_PACKET_SIZE (unsigned int)(((MAX_PAYLOAD_SIZE / 1)) | (0x00 << 11)) + + // #define MAX_PAYLOAD_SIZE 2048 // for high speed with two transcations every one micro frame + // #define VIDEO_PACKET_SIZE (unsigned int)(((MAX_PAYLOAD_SIZE / 2)) | (0x01 << 11)) + + // #define MAX_PAYLOAD_SIZE 3072 // for high speed with three transcations every one micro frame + // #define VIDEO_PACKET_SIZE (unsigned int)(((MAX_PAYLOAD_SIZE / 3)) | (0x02 << 11)) + + #else + #define MAX_PAYLOAD_SIZE 1020 + #define VIDEO_PACKET_SIZE (unsigned int)(((MAX_PAYLOAD_SIZE / 1)) | (0x00 << 11)) + #endif + +- Usually only need to modify WIDTH and HEIGHT + +.. code-block:: C + + #define WIDTH (unsigned int)(640) + #define HEIGHT (unsigned int)(480) + + #define CAM_FPS (30) + #define INTERVAL (unsigned long)(10000000 / CAM_FPS) + #define MIN_BIT_RATE (unsigned long)(WIDTH * HEIGHT * 16 * CAM_FPS) //16 bit + #define MAX_BIT_RATE (unsigned long)(WIDTH * HEIGHT * 16 * CAM_FPS) + #define MAX_FRAME_SIZE (unsigned long)(WIDTH * HEIGHT * 2) + +- USB endpoint configuration, default interval is 1, which is 1ms in full-speed mode and 125us in high-speed mode. Synchronization type uses asynchronous mode. + +.. code-block:: C + + /* 1.2.2.2 Standard VideoStream Isochronous Video Data Endpoint Descriptor */ + USB_ENDPOINT_DESCRIPTOR_INIT(VIDEO_IN_EP, 0x05, VIDEO_PACKET_SIZE, 0x01), + + +- Use `usbd_video_stream_start_write` to transfer data. The final **do_copy** option indicates whether to copy data to packet_buffer. +If copy is not selected, header information will be directly filled in the original image data and sent directly, achieving zero copy functionality. + +- Because static data is provided and cannot be modified, a new frame_buffer needs to be allocated for image transmission. In actual camera integration scenarios, dynamic data is used and the camera's data buffer can be used directly. + + +.. code-block:: C + + void usbd_video_iso_callback(uint8_t busid, uint8_t ep, uint32_t nbytes) + { + if (usbd_video_stream_split_transfer(busid, ep)) { + /* one frame has done */ + iso_tx_busy = false; + } + } + + USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t packet_buffer[MAX_PAYLOAD_SIZE]; + USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t frame_buffer[32 * 1024]; + + void video_test(uint8_t busid) + { + memset(packet_buffer, 0, sizeof(packet_buffer)); + + while (1) { + if (tx_flag) { + iso_tx_busy = true; + memcpy(frame_buffer, cherryusb_mjpeg, sizeof(cherryusb_mjpeg)); // cherryusb_mjpeg is a static MJPEG frame buffer, so we need copy it to frame_buffer + usbd_video_stream_start_write(busid, VIDEO_IN_EP, packet_buffer, (uint8_t *)frame_buffer, sizeof(cherryusb_mjpeg), false); + while (iso_tx_busy) { + if (tx_flag == 0) { + break; + } + } + } + } + } \ No newline at end of file diff --git a/docs/en/demo/usbd_webusb.rst b/docs/en/demo/usbd_webusb.rst new file mode 100755 index 00000000..3a6d3418 --- /dev/null +++ b/docs/en/demo/usbd_webusb.rst @@ -0,0 +1,21 @@ +WebUSB Device +================= + +This demo mainly demonstrates webusb functionality. Webusb is mainly used to pop up web pages and access USB devices. The example uses webusb_hid_template.c. + +- When registering descriptors, just register BOS, MSOSV2, WEBUSB descriptors. + +.. code-block:: C + + usbd_bos_desc_register(busid, &bos_desc); + usbd_msosv2_desc_register(busid, &msosv2_desc); + usbd_webusb_desc_register(busid, &webusb_url_desc); + +- Add an interface descriptor for webusb + +.. code-block:: C + + USB_INTERFACE_DESCRIPTOR_INIT(USBD_WEBUSB_INTF_NUM, 0x00, 0x00, 0xff, 0x00, 0x00, 0x00) + +- The rest use hid descriptors, no further elaboration +- After enumeration is completed, webpage information will pop up in the lower right corner of the computer, click to open the webpage \ No newline at end of file diff --git a/docs/en/demo/usbd_winusb.rst b/docs/en/demo/usbd_winusb.rst new file mode 100755 index 00000000..059ff1f3 --- /dev/null +++ b/docs/en/demo/usbd_winusb.rst @@ -0,0 +1,55 @@ +WinUSB Device +================= + +This section mainly introduces the winusb driver. Winusb is a general driver provided by Windows to allow users to access USB custom class devices in a user-friendly manner. It is essentially CDC ACM, but without baud rate setting commands. +WINUSB versions are divided into V1/V2 versions according to USB versions. V2 version requires BOS descriptor, while V1 version does not. **V2 version requires setting USB2.1 version number in device descriptor**. + +.. note:: Changing any winusb descriptor configuration may result in successful enumeration but inability to recognize the device. You need to delete all registry entries under Computer\HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\usbflags, then unplug and replug the device to take effect. + +- V1 version descriptor registration + +.. code-block:: C + + const struct usb_descriptor winusbv1_descriptor = { + .device_descriptor_callback = device_descriptor_callback, + .config_descriptor_callback = config_descriptor_callback, + .device_quality_descriptor_callback = device_quality_descriptor_callback, + .string_descriptor_callback = string_descriptor_callback, + .msosv1_descriptor = &msosv1_desc + }; + + OR + + usbd_msosv1_desc_register(busid, &msosv1_desc); + +- V2 version descriptor registration + +.. code-block:: C + + const struct usb_descriptor winusbv2_descriptor = { + .device_descriptor_callback = device_descriptor_callback, + .config_descriptor_callback = config_descriptor_callback, + .device_quality_descriptor_callback = device_quality_descriptor_callback, + .string_descriptor_callback = string_descriptor_callback, + .msosv2_descriptor = &msosv2_desc, + .bos_descriptor = &bos_desc, + }; + + OR + + usbd_bos_desc_register(busid, &bos_desc); + usbd_msosv2_desc_register(busid, &msosv2_desc); + + +- Interface descriptor registration + +.. code-block:: C + + /* Interface 0 */ + USB_INTERFACE_DESCRIPTOR_INIT(0x00, 0x00, 0x02, 0xFF, 0x00, 0x00, 0x02), + /* Endpoint OUT 2 */ + USB_ENDPOINT_DESCRIPTOR_INIT(WINUSB_OUT_EP, USB_ENDPOINT_TYPE_BULK, WINUSB_EP_MPS, 0x00), + /* Endpoint IN 1 */ + USB_ENDPOINT_DESCRIPTOR_INIT(WINUSB_IN_EP, USB_ENDPOINT_TYPE_BULK, WINUSB_EP_MPS, 0x00), + +- Read and write operations are the same as CDC ACM, no further elaboration \ No newline at end of file diff --git a/docs/en/demo/usbh_audio.rst b/docs/en/demo/usbh_audio.rst new file mode 100755 index 00000000..387271f6 --- /dev/null +++ b/docs/en/demo/usbh_audio.rst @@ -0,0 +1,4 @@ +Audio Host +================= + +.. note:: Host UAC is commercially charged. Please contact the official for purchase authorization. \ No newline at end of file diff --git a/docs/en/demo/usbh_bluetooth.rst b/docs/en/demo/usbh_bluetooth.rst new file mode 100755 index 00000000..5b06f502 --- /dev/null +++ b/docs/en/demo/usbh_bluetooth.rst @@ -0,0 +1,2 @@ +BTBLE Host +================= diff --git a/docs/en/demo/usbh_hid.rst b/docs/en/demo/usbh_hid.rst new file mode 100755 index 00000000..7929179d --- /dev/null +++ b/docs/en/demo/usbh_hid.rst @@ -0,0 +1,55 @@ +HID Host +================= + +This section mainly introduces the use of Host HID class. + +- Create a one-time thread in HID enumeration completion callback + +.. code-block:: C + + + void usbh_hid_run(struct usbh_hid *hid_class) + { + usb_osal_thread_create("usbh_hid", 2048, CONFIG_USBHOST_PSC_PRIO + 1, usbh_hid_thread, hid_class); + } + + void usbh_hid_stop(struct usbh_hid *hid_class) + { + } + + +- Here we use the asynchronous operation of usbh_submit_urb, process data in interrupt and continue to receive next data. + +.. code-block:: C + + static void usbh_hid_thread(void *argument) + { + int ret; + struct usbh_hid *hid_class = (struct usbh_hid *)argument; + ; + + /* test with only one buffer, if you have more hid class, modify by yourself */ + + /* Suggest you to use timer for int transfer and use ep interval */ + usbh_int_urb_fill(&hid_class->intin_urb, hid_class->hport, hid_class->intin, hid_buffer, hid_class->intin->wMaxPacketSize, 0, usbh_hid_callback, hid_class); + ret = usbh_submit_urb(&hid_class->intin_urb); + if (ret < 0) { + goto delete; + } + // clang-format off + delete: + usb_osal_thread_delete(NULL); + // clang-format on + } + +- Of course, you can also not use asynchronous operations, but use synchronous operations with timeout. +- HID uses interrupt transfer, so normally we need to set a timer based on **bInterval** to trigger interrupt transfer at regular intervals. This is not used in the demo. If you have precise time requirements, you can choose to use a timer to trigger asynchronous sending. +- Taking hub communication as an example, a one-time timer is used, but a periodic timer can also be used. + +.. code-block:: C + + hub->int_timer = usb_osal_timer_create("hubint_tim", USBH_GET_URB_INTERVAL(hub->intin->bInterval, hport->speed) / 1000, hub_int_timeout, hub, 0); + +.. note:: + + Here `USBH_GET_URB_INTERVAL` is a macro definition used to calculate the URB transfer interval time based on binterval. The unit is us, while the timer minimum is ms, so it needs to be divided by 1000. For intervals less than or equal to 1ms, no timer is needed. \ No newline at end of file diff --git a/docs/en/demo/usbh_msc.rst b/docs/en/demo/usbh_msc.rst new file mode 100755 index 00000000..b47abdc8 --- /dev/null +++ b/docs/en/demo/usbh_msc.rst @@ -0,0 +1,56 @@ +MSC Host +================= + +This section mainly introduces the use of Host MSC. Read and write functions are implemented with the help of FATFS. + +- Register a thread in the callback after MSC enumeration is completed, used for read and write operations. + +.. code-block:: C + + void usbh_msc_run(struct usbh_msc *msc_class) + { + usb_osal_thread_create("usbh_msc", 2048, CONFIG_USBHOST_PSC_PRIO + 1, usbh_msc_thread, msc_class); + } + + void usbh_msc_stop(struct usbh_msc *msc_class) + { + } + + +- Without using fatfs, directly use usbh_msc_scsi_read10 or usbh_msc_scsi_write10 functions for read and write operations. +- If using fatfs, you need to call fatfs interfaces in usbh_msc_thread for read and write operations. For MSC read/write adaptation to fatfs, refer to `platform/fatfs/usbh_fatfs.c` + +.. code-block:: C + + static void usbh_msc_thread(void *argument) + { + int ret; + struct usbh_msc *msc_class = (struct usbh_msc *)argument; + + /* test with only one buffer, if you have more msc class, modify by yourself */ + #if 1 + /* get the partition table */ + ret = usbh_msc_scsi_read10(msc_class, 0, partition_table, 1); + if (ret < 0) { + USB_LOG_RAW("scsi_read10 error,ret:%d\r\n", ret); + goto delete; + } + for (uint32_t i = 0; i < 512; i++) { + if (i % 16 == 0) { + USB_LOG_RAW("\r\n"); + } + USB_LOG_RAW("%02x ", partition_table[i]); + } + USB_LOG_RAW("\r\n"); + #endif + + #if TEST_USBH_MSC_FATFS + usb_msc_fatfs_test(); + #endif + // clang-format off + delete: + usb_osal_thread_delete(NULL); + // clang-format on + } + +- Finally, after processing is completed or failed, delete the thread. \ No newline at end of file diff --git a/docs/en/demo/usbh_net.rst b/docs/en/demo/usbh_net.rst new file mode 100755 index 00000000..13069563 --- /dev/null +++ b/docs/en/demo/usbh_net.rst @@ -0,0 +1,167 @@ +Network Host +================= + +This section mainly introduces the use of Host USB network cards. The following USB ne- Because the USB network card has been internally connected to LWIP, users can directly use LWIP APIs without worrying about USB implementation. + +USB Network Card LWIP Configuration Macro Related Notes +----------------------------------------------------------- + +**LWIP_TCPIP_CORE_LOCKING_INPUT** is used to not use lwip built-in tcpip thread, but use USB's own receive processing thread. + +**LWIP_TCPIP_CORE_LOCKING** is enabled by default in current lwip versions, and it is also recommended to be mandatory. + +**PBUF_POOL_BUFSIZE** is recommended to be greater than 1600, used with LWIP_TCPIP_CORE_LOCKING_INPUT, because we provide zero copy method using static pbuf instead of copying data into pbuf. + +**TCPIP_THREAD_STACKSIZE** is recommended to be greater than 1K to prevent stack overflow.are currently supported and tested: + +- 4G network cards: EC20(ECM/RNDIS), mobile phones (RNDIS), SIMCOM7600(RNDIS), ML307R(RNDIS), AIR780(RNDIS) + +.. caution:: Please note that some 4G network cards do not have auto-dial functionality by default. Please replace the firmware or use AT commands to configure auto-dial, otherwise you cannot get an IP. + +- USB Ethernet cards: ASIX AX88772, REALTEK RTL8152 +- USB WIFI cards: Bouffalo Lab BL616 (RNDIS/ECM) + +USB Network Card Related Macros and Files +-------------------------------------------------- + +The network card related macros are as follows, mainly used to register network card drivers according to different network components: + +.. code-block:: C + + // #define CONFIG_USBHOST_PLATFORM_CDC_ECM + // #define CONFIG_USBHOST_PLATFORM_CDC_RNDIS + // #define CONFIG_USBHOST_PLATFORM_CDC_NCM + // #define CONFIG_USBHOST_PLATFORM_ASIX + // #define CONFIG_USBHOST_PLATFORM_RTL8152 + +.. note:: If Kconfig system is used, the above macros are automatically generated. For other platforms, please define manually. + +USB network card transmission layer has been connected to relevant network components, listed as follows: + +- Custom OS + LWIP please use **platform/lwip/usbh_lwip.c**, need to include this file yourself and enable the above relevant macros. Call `tcpip_init(NULL, NULL)` before initializing USB +- RT-THREAD + LWIP please use **platform/rtthread/usbh_lwip.c**, automatically select this file after enabling corresponding network card driver in Kconfig, automatically call `tcpip_init(NULL, NULL)` after selecting rt-thread lwip +- ESP-IDF + LWIP please use **platform/freertos/usbh_net.c**, automatically select this file after enabling corresponding network card driver in Kconfig, and call `esp_netif_init()` + `esp_event_loop_create_default()` before initializing USB +- NUTTX + NUTTX network component please use **platform/nuttx/usbh_net.c**, automatically select this file after enabling corresponding network card driver in Kconfig, automatically call after selecting network component + +.. note:: If adding code yourself, don't forget to add USB network card driver related source files, such as **class/usbh_cdc_ecm.c**. So we recommend using with corresponding platforms to save the trouble of adding files yourself + +USB Network Card Connection Process +--------------------------------------------- + +The following example shows the LWIP connection process. + +- After USB network card enumeration is completed, the `usbh_xxx_run` function will be **automatically** called, at which time netif driver is registered, and DHCP client and IP acquisition timer are started. + +.. code-block:: C + + void usbh_cdc_ecm_run(struct usbh_cdc_ecm *cdc_ecm_class) + { + struct netif *netif = &g_cdc_ecm_netif; + + netif->hwaddr_len = 6; + memcpy(netif->hwaddr, cdc_ecm_class->mac, 6); + + IP4_ADDR(&g_ipaddr, 0, 0, 0, 0); + IP4_ADDR(&g_netmask, 0, 0, 0, 0); + IP4_ADDR(&g_gateway, 0, 0, 0, 0); + + netif = netif_add(netif, &g_ipaddr, &g_netmask, &g_gateway, NULL, usbh_cdc_ecm_if_init, tcpip_input); + netif_set_default(netif); + while (!netif_is_up(netif)) { + } + + dhcp_handle = usb_osal_timer_create("dhcp", 200, dhcp_timeout, netif, true); + if (dhcp_handle == NULL) { + USB_LOG_ERR("timer creation failed! \r\n"); + while (1) { + } + } + + usb_osal_thread_create("usbh_cdc_ecm_rx", 2048, CONFIG_USBHOST_PSC_PRIO + 1, usbh_cdc_ecm_rx_thread, NULL); + #if LWIP_DHCP + dhcp_start(netif); + usb_osal_timer_start(dhcp_handle); + #endif + } + +- `usbh_lwip_eth_output_common` is used to assemble transmitted pbuf into USB network card data packets +- `usbh_lwip_eth_input_common` is used to assemble USB network card data into pbuf +- Actual network card transmission and reception processing + +.. code-block:: C + + static err_t usbh_cdc_ecm_linkoutput(struct netif *netif, struct pbuf *p) + { + int ret; + (void)netif; + + usbh_lwip_eth_output_common(p, usbh_cdc_ecm_get_eth_txbuf()); + ret = usbh_cdc_ecm_eth_output(p->tot_len); + if (ret < 0) { + return ERR_BUF; + } else { + return ERR_OK; + } + } + + void usbh_cdc_ecm_eth_input(uint8_t *buf, uint32_t buflen) + { + usbh_lwip_eth_input_common(&g_cdc_ecm_netif, buf, buflen); + } + +- After the USB network card is unplugged, the `usbh_xxx_stop` function will be **automatically** called, at which time you need to stop the DHCP client, delete the timer, and remove the netif. + +.. code-block:: C + + void usbh_cdc_ecm_stop(struct usbh_cdc_ecm *cdc_ecm_class) + { + struct netif *netif = &g_cdc_ecm_netif; + (void)cdc_ecm_class; + + #if LWIP_DHCP + dhcp_stop(netif); + dhcp_cleanup(netif); + usb_osal_timer_delete(dhcp_handle); + #endif + netif_set_down(netif); + netif_remove(netif); + } + +- Because the USB network card has been internally connected to LWIP, users can directly use LWIP APIs without worrying about USB implementation. + +USB Network Card LWIP Configuration Macro Related Notes +-------------------------------------------------------------- + +**LWIP_TCPIP_CORE_LOCKING_INPUT** is used to not use lwip built-in tcpip thread, but use USB's own receive processing thread. + +**LWIP_TCPIP_CORE_LOCKING** is enabled by default in current lwip versions, and it is also recommended to be mandatory. + +**PBUF_POOL_BUFSIZE** is recommended to be greater than 1600, used with LWIP_TCPIP_CORE_LOCKING_INPUT, because we provide zero copy method using static pbuf instead of copying data into pbuf. + +**TCPIP_THREAD_STACKSIZE** is recommended to be greater than 1K to prevent stack overflow. + +.. code-block:: C + + #if LWIP_TCPIP_CORE_LOCKING_INPUT != 1 + #warning suggest you to set LWIP_TCPIP_CORE_LOCKING_INPUT to 1, usb handles eth input with own thread + #endif + + #if LWIP_TCPIP_CORE_LOCKING != 1 + #error must set LWIP_TCPIP_CORE_LOCKING to 1 + #endif + + #if PBUF_POOL_BUFSIZE < 1600 + #error PBUF_POOL_BUFSIZE must be larger than 1600 + #endif + + #if TCPIP_THREAD_STACKSIZE < 1024 + #error TCPIP_THREAD_STACKSIZE must be >= 1024 + #endif + + +Summary +-------------- + +.. note:: Through the above content, we can see that CherryUSB's support for USB network cards is very comprehensive. Users only need to enable corresponding macros or check options to achieve automatic recognition and driver registration of USB network cards, without manually initializing network card related configurations. Users only need to focus on the application layer, which greatly facilitates user usage. + +For specific porting articles, please refer to developers' notes https://club.rt-thread.org/ask/article/5cf3e9e0b2d95800.html \ No newline at end of file diff --git a/docs/en/demo/usbh_serial.rst b/docs/en/demo/usbh_serial.rst new file mode 100755 index 00000000..03d89f04 --- /dev/null +++ b/docs/en/demo/usbh_serial.rst @@ -0,0 +1,196 @@ +Serial Host +================= + +This section mainly introduces the usage of the Host serial framework. The Serial framework currently supports CDC ACM, FTDI, CP210x, CH34x, PL2303, and GSM drivers. + +.. figure:: img/usbh_serial.png + +Currently supports two usage methods: one is using native CherryUSB usbhost serial API for operations, and the other is based on platform-wrapped APIs such as RT-Thread device API and NuttX POSIX API. + +The following demonstrates using CherryUSB usbhost serial API for serial loopback testing with blocking transmission and asynchronous reception: + +.. code-block:: C + + struct usbh_serial *serial; + + serial = usbh_serial_open("/dev/ttyACM0", USBH_SERIAL_O_RDWR | USBH_SERIAL_O_NONBLOCK); + if (serial == NULL) { + serial = usbh_serial_open("/dev/ttyUSB0", USBH_SERIAL_O_RDWR | USBH_SERIAL_O_NONBLOCK); + if (serial == NULL) { + USB_LOG_RAW("no serial device found\r\n"); + goto delete; + } + } + + struct usbh_serial_termios termios; + + memset(&termios, 0, sizeof(termios)); + termios.baudrate = 115200; + termios.stopbits = 0; + termios.parity = 0; + termios.databits = 8; + termios.rtscts = false; + termios.rx_timeout = 0; + ret = usbh_serial_control(serial, USBH_SERIAL_CMD_SET_ATTR, &termios); + if (ret < 0) { + USB_LOG_RAW("set serial attr error, ret:%d\r\n", ret); + goto delete_with_close; + } + + serial_tx_bytes = 0; + while (1) { + ret = usbh_serial_write(serial, serial_tx_buffer, sizeof(serial_tx_buffer)); + if (ret < 0) { + USB_LOG_RAW("serial write error, ret:%d\r\n", ret); + goto delete_with_close; + } else { + serial_tx_bytes += ret; + + if (serial_tx_bytes == SERIAL_TEST_LEN) { + USB_LOG_RAW("send over\r\n"); + break; + } + } + } + + volatile uint32_t wait_timeout = 0; + serial_rx_bytes = 0; + while (1) { + ret = usbh_serial_read(serial, &serial_rx_data[serial_rx_bytes], SERIAL_TEST_LEN - serial_rx_bytes); + if (ret < 0) { + USB_LOG_RAW("serial read error, ret:%d\r\n", ret); + goto delete_with_close; + } else { + serial_rx_bytes += ret; + + if (serial_rx_bytes == SERIAL_TEST_LEN) { + USB_LOG_RAW("receive over\r\n"); + for (uint32_t i = 0; i < SERIAL_TEST_LEN; i++) { + if (serial_rx_data[i] != 0xa5) { + USB_LOG_RAW("serial loopback data error at index %d, data: 0x%02x\r\n", (unsigned int)i, serial_rx_data[i]); + goto delete_with_close; + } + } + serial_test_success = true; + break; + } + } + wait_timeout++; + + if (wait_timeout > 500) { // 5s + USB_LOG_RAW("serial read timeout\r\n"); + goto delete_with_close; + } + + usb_osal_msleep(10); + } + + usbh_serial_close(serial); + +.. caution:: Note that the example uses a simple send-then-read approach, so the total length sent cannot exceed CONFIG_USBHOST_SERIAL_RX_SIZE. For normal TX/RX usage, please perform them separately. + +Users need to consider the following three scenarios: + +- USB2TTL device + baud rate enabled (USB2TTL devices must enable baud rate), in this case you need to use `usbh_serial_write` and `usbh_serial_read` to send and receive data, **and read operations need to be timely to prevent ringbuf data overflow and packet loss**. Cannot use `usbh_serial_cdc_write_async` and `usbh_serial_cdc_read_async` + +- Pure USB device + baud rate not started, in this case you can use `usbh_serial_cdc_write_async` and `usbh_serial_cdc_read_async` for asynchronous send/receive data. For blocking, you can use `usbh_serial_write`, but cannot use `usbh_serial_read`. + +- Pure USB device + baud rate started, same as 1, but the reception rate will be discounted (because of an extra layer of ringbuf). In this case, `usbh_serial_cdc_write_async` and `usbh_serial_cdc_read_async` cannot be used either. **If it is a GSM device, please use the first scenario**. + +.. note:: Simply put, if receiving data requires going through a ringbuf layer, please use the first scenario. + +.. code-block:: C + + [I/usbh_hub] New full-speed device on Bus 0, Hub 1, Port 1 connected + [I/usbh_core] New device found,idVendor:10c4,idProduct:ea60,bcdDevice:0100 + [I/usbh_core] The device has 1 bNumConfigurations + [I/usbh_core] The device has 1 interfaces + [I/usbh_core] Enumeration success, start loading class driver + [I/usbh_core] Loading cp210x class driver on interface 0 + [I/usbh_cp210x] chip partnum: 0x02 + [I/usbh_cp210x] ulAmountInInQueue: 0, ulAmountInOutQueue: 0 + [I/usbh_serial] Ep=81 Attr=02 Mps=64 Interval=00 Mult=00 + [I/usbh_serial] Ep=01 Attr=02 Mps=64 Interval=00 Mult=00 + [I/usbh_serial] Register Serial Class: /dev/ttyUSB0 (cp210x) + start serial loopback test, len: 1024 + send over + receive over + serial loopback test success + [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB0 (cp210x) + [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected + [I/usbh_hub] New high-speed device on Bus 0, Hub 1, Port 1 connected + [I/usbh_core] New device found,idVendor:0403,idProduct:6010,bcdDevice:0700 + [I/usbh_core] The device has 1 bNumConfigurations + [I/usbh_core] The device has 2 interfaces + [I/usbh_core] Enumeration success, start loading class driver + [I/usbh_core] Loading ftdi class driver on interface 0 + [I/usbh_ftdi] chip name: FT2232H + [I/usbh_serial] Ep=81 Attr=02 Mps=512 Interval=00 Mult=00 + [I/usbh_serial] Ep=02 Attr=02 Mps=512 Interval=00 Mult=00 + [I/usbh_serial] Register Serial Class: /dev/ttyUSB0 (ftdi) + [I/usbh_core] Loading ftdi class driver on interface 1 + [I/usbh_ftdi] chip name: FT2232H + [I/usbh_serial] Ep=83 Attr=02 Mps=512 Interval=00 Mult=00 + [I/usbh_serial] Ep=04 Attr=02 Mps=512 Interval=00 Mult=00 + [I/usbh_serial] Register Serial Class: /dev/ttyUSB1 (ftdi) + start serial loopback test, len: 1024 + send over + receive over + serial loopback test success + [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB0 (ftdi) + [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB1 (ftdi) + [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected + [I/usbh_hub] New full-speed device on Bus 0, Hub 1, Port 1 connected + [I/usbh_core] New device found,idVendor:067b,idProduct:2303,bcdDevice:0300 + [I/usbh_core] The device has 1 bNumConfigurations + [I/usbh_core] The device has 1 interfaces + [I/usbh_core] Enumeration success, start loading class driver + [I/usbh_core] Loading pl2303 class driver on interface 0 + [I/usbh_pl2303] Ep=81 Attr=03 Mps=10 Interval=01 Mult=00 + [I/usbh_pl2303] chip type: PL2303HX + [I/usbh_serial] Ep=02 Attr=02 Mps=64 Interval=00 Mult=00 + [I/usbh_serial] Ep=83 Attr=02 Mps=64 Interval=00 Mult=00 + [I/usbh_serial] Register Serial Class: /dev/ttyUSB0 (pl2303) + start serial loopback test, len: 1024 + send over + receive over + serial loopback test success + [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB0 (pl2303) + [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected + [W/usbh_hub] Failed to enable port 1 + [I/usbh_hub] New full-speed device on Bus 0, Hub 1, Port 1 connected + [I/usbh_core] New device found,idVendor:1a86,idProduct:7523,bcdDevice:0264 + [I/usbh_core] The device has 1 bNumConfigurations + [I/usbh_core] The device has 1 interfaces + [I/usbh_core] Enumeration success, start loading class driver + [I/usbh_core] Loading ch34x class driver on interface 0 + [I/usbh_ch43x] Ep=81 Attr=03 Mps=8 Interval=01 Mult=00 + [I/usbh_ch43x] chip version: 0x31 + [I/usbh_serial] Ep=82 Attr=02 Mps=32 Interval=00 Mult=00 + [I/usbh_serial] Ep=02 Attr=02 Mps=32 Interval=00 Mult=00 + [I/usbh_serial] Register Serial Class: /dev/ttyUSB0 (ch34x) + start serial loopback test, len: 1024 + send over + receive over + serial loopback test success + [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB0 (ch34x) + [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected + [I/usbh_hub] New full-speed device on Bus 0, Hub 1, Port 1 connected + [I/usbh_core] New device found,idVendor:42bf,idProduct:b210,bcdDevice:0217 + [I/usbh_core] The device has 1 bNumConfigurations + [I/usbh_core] The device has 3 interfaces + [I/usbh_core] Enumeration success, start loading class driver + [E/usbh_core] Do not support Class:0xff, Subclass:0x01, Protocl:0x00 on interface 0 + [I/usbh_core] Loading cdc_acm class driver on interface 1 + [I/usbh_cdc_acm] Ep=85 Attr=03 Mps=64 Interval=00 Mult=00 + [I/usbh_serial] Ep=04 Attr=02 Mps=64 Interval=00 Mult=00 + [I/usbh_serial] Ep=83 Attr=02 Mps=64 Interval=00 Mult=00 + [I/usbh_serial] Register Serial Class: /dev/ttyACM0 (cdc_acm) + [I/usbh_core] Loading cdc_data class driver on interface 2 + start serial loopback test, len: 1024 + send over + receive over + serial loopback test success + [I/usbh_serial] Unregister Serial Class: /dev/ttyACM0 (cdc_acm) + [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected + diff --git a/docs/en/demo/usbh_vendor.rst b/docs/en/demo/usbh_vendor.rst new file mode 100755 index 00000000..09afe1cd --- /dev/null +++ b/docs/en/demo/usbh_vendor.rst @@ -0,0 +1,127 @@ +Writing Vendor Host Driver +============================================ + +This section mainly introduces how to write a vendor host driver. + +- First copy a class/template/usbh_xxx.c file + +- Define class driver and use CLASS_INFO_DEFINE prefix, so that after enumeration is completed, the protocol stack automatically finds the corresponding driver through usbd_class_find_driver. + +.. code-block:: C + + static const struct usbh_class_driver xxx_class_driver = { + .driver_name = "xxx", + .connect = usbh_xxx_connect, + .disconnect = usbh_xxx_disconnect + }; + + CLASS_INFO_DEFINE const struct usbh_class_info xxx_class_info = { + .match_flags = USB_CLASS_MATCH_INTF_CLASS | USB_CLASS_MATCH_INTF_SUBCLASS | USB_CLASS_MATCH_INTF_PROTOCOL, + .bInterfaceClass = 0, + .bInterfaceSubClass = 0, + .bInterfaceProtocol = 0, + .id_table = NULL, + .class_driver = &xxx_class_driver + }; + + +- Implement connect and disconnect functions. In the connect function, you need to allocate an xxx_class structure. In the disconnect function, release the urb and xxx_class. + +.. code-block:: C + + struct usbh_xxx { + struct usbh_hubport *hport; + struct usb_endpoint_descriptor *xxxin; + struct usb_endpoint_descriptor *xxxout; + struct usbh_urb xxxin_urb; + struct usbh_urb xxxout_urb; + + uint8_t intf; /* interface number */ + uint8_t minor; + + void *user_data; + }; + + static int usbh_xxx_connect(struct usbh_hubport *hport, uint8_t intf) + { + struct usb_endpoint_descriptor *ep_desc; + int ret; + + struct usbh_xxx *xxx_class = usbh_xxx_class_alloc(); + if (xxx_class == NULL) { + USB_LOG_ERR("Fail to alloc xxx_class\r\n"); + return -USB_ERR_NOMEM; + } + + return ret; + } + + + static int usbh_xxx_disconnect(struct usbh_hubport *hport, uint8_t intf) + { + int ret = 0; + + struct usbh_xxx *xxx_class = (struct usbh_xxx *)hport->config.intf[intf].priv; + + if (xxx_class) { + if (xxx_class->xxxin) { + usbh_kill_urb(&xxx_class->xxxin_urb); + } + + if (xxx_class->xxxout) { + usbh_kill_urb(&xxx_class->xxxout_urb); + } + + if (hport->config.intf[intf].devname[0] != '\0') { + USB_LOG_INFO("Unregister xxx Class:%s\r\n", hport->config.intf[intf].devname); + usbh_xxx_stop(xxx_class); + } + + usbh_xxx_class_free(xxx_class); + } + + return ret; + } + +- Initialize endpoints + +.. code-block:: C + + for (uint8_t i = 0; i < hport->config.intf[intf].altsetting[0].intf_desc.bNumEndpoints; i++) { + ep_desc = &hport->config.intf[intf].altsetting[0].ep[i].ep_desc; + if (ep_desc->bEndpointAddress & 0x80) { + USBH_EP_INIT(xxx_class->intin, ep_desc); + } else { + USBH_EP_INIT(xxx_class->intout, ep_desc); + } + } + +- Finally design send/receive APIs, design them as synchronous or asynchronous according to actual conditions. + +.. code-block:: C + + int usbh_xxx_in_transfer(struct usbh_xxx *xxx_class, uint8_t *buffer, uint32_t buflen, uint32_t timeout) + { + int ret; + struct usbh_urb *urb = &xxx_class->xxxin_urb; + + usbh_xxx_urb_fill(urb, xxx_class->hport, xxx_class->xxxin, buffer, buflen, timeout, NULL, NULL); + ret = usbh_submit_urb(urb); + if (ret == 0) { + ret = urb->actual_length; + } + return ret; + } + + int usbh_xxx_out_transfer(struct usbh_xxx *xxx_class, uint8_t *buffer, uint32_t buflen, uint32_t timeout) + { + int ret; + struct usbh_urb *urb = &xxx_class->xxxout_urb; + + usbh_xxx_urb_fill(urb, xxx_class->hport, xxx_class->xxxout, buffer, buflen, timeout, NULL, NULL); + ret = usbh_submit_urb(urb); + if (ret == 0) { + ret = urb->actual_length; + } + return ret; + } \ No newline at end of file diff --git a/docs/en/demo/usbh_video.rst b/docs/en/demo/usbh_video.rst new file mode 100755 index 00000000..646b2c27 --- /dev/null +++ b/docs/en/demo/usbh_video.rst @@ -0,0 +1,4 @@ +Video Host +================= + +.. note:: Host UVC is commercially charged. Please contact official support to purchase authorization. \ No newline at end of file diff --git a/docs/en/demo/usbh_wifi.rst b/docs/en/demo/usbh_wifi.rst new file mode 100755 index 00000000..588e8131 --- /dev/null +++ b/docs/en/demo/usbh_wifi.rst @@ -0,0 +1,2 @@ +WIFI Host +================= diff --git a/docs/en/index.rst b/docs/en/index.rst new file mode 100755 index 00000000..25a7cc4f --- /dev/null +++ b/docs/en/index.rst @@ -0,0 +1,160 @@ +.. CherryUSB User Guide documentation master file, created by + sphinx-quickstart on Thu Nov 21 10:50:33 2019. + You can adapt this file completely to your liking, but it should at least + contain the root `toctree` directive. + +CherryUSB User Guide +==================================================================== + +CherryUSB is a small, lightweight, portable USB host and device protocol stack for embedded systems. CherryUSB offers the following advantages: + +**Easy to Learn USB** + +To facilitate user learning of USB fundamentals, enumeration, driver loading, and IP drivers, the written code has the following advantages: + +- Streamlined code with simple logic and no complex C language syntax +- Tree-structured programming with progressive code layers +- Templated and simplified Class drivers and porting drivers +- Clear API categorization (Device: initialization, class registration, command callbacks, data transmission; Host: initialization, class discovery, data transmission) + +**Easy to Use USB** + +To facilitate user interaction with USB interfaces, considering users' familiarity with UART and DMA, the designed data transmission interface has the following advantages: + +- Equivalent to using UART TX DMA/UART RX DMA +- No length restrictions on transmission/reception; users don't need to worry about USB packetization (porting drivers handle packetization) + +**Easy to Achieve USB Performance** + +Considering USB performance requirements to reach theoretical USB hardware bandwidth, the designed data transmission interface has the following advantages: + +- Porting drivers directly interface with registers without abstraction layer encapsulation +- Memory zero copy +- DMA mode used when IP supports DMA (DMA provides hardware packetization functionality) +- No length restrictions, facilitating hardware DMA interfacing and maximizing DMA advantages +- Packetization handled in interrupt context + +**Device Protocol Stack Overall Execution Flow** + +.. figure:: usbdev.svg + +**Host Protocol Stack Overall Execution Flow** + +.. figure:: usbhost.svg + +**Other Related Links** + +- **Video Tutorial**: https://www.bilibili.com/cheese/play/ss707687201 +- **GitHub**: https://github.com/sakumisu/CherryUSB +- **CherryUSB Theoretical Analysis and Application Practice - Hans Journal**: https://www.hanspub.org/journal/paperinformation?paperid=126903 + +.. toctree:: + :maxdepth: 1 + :caption: Quick Start + + quick_start/start + quick_start/demo + quick_start/transplant + quick_start/rtthread + quick_start/q&a + quick_start/migration + quick_start/share + quick_start/opensource + +.. toctree:: + :maxdepth: 1 + :caption: USB Basic Knowledge + + usb/usb2.0_basic + usb/usb3.0_basic + usb/usb_desc + usb/usb_request + usb/usb_enum + usb/usb_ext + +.. toctree:: + :maxdepth: 1 + :caption: API Manual + + api/api_device + api/api_host + api/api_port + api/api_config + +.. toctree:: + :maxdepth: 1 + :caption: Class Guide + + class/class_cdc + class/class_hid + class/class_msc + class/class_audio + class/class_video + class/winusb + +.. toctree:: + :maxdepth: 1 + :caption: Examples + + demo/usbd_cdc_acm + demo/usbd_hid + demo/usbd_msc + demo/usbd_audiov1 + demo/usbd_audiov2 + demo/usbd_video + demo/usbd_winusb + demo/usbd_webusb + demo/usbd_rndis + demo/usbd_ecm + demo/usbd_adb + demo/usbd_mtp + demo/usbh_serial + demo/usbh_hid + demo/usbh_msc + demo/usbh_net + demo/usbh_bluetooth + demo/usbh_wifi + demo/usbh_audio + demo/usbh_video + demo/usb_otg + demo/usbd_vendor + demo/usbh_vendor + +.. toctree:: + :maxdepth: 1 + :caption: USB IP Introduction + + usbip/ohci + usbip/ehci + usbip/xhci + usbip/chipidea + usbip/dwc2 + usbip/musb + usbip/fotg210 + usbip/cdns2 + usbip/cdns3 + usbip/dwc3 + +.. toctree:: + :maxdepth: 1 + :caption: Tools Usage + + tools/index + +.. toctree:: + :maxdepth: 1 + :caption: Version Information + + version + +.. toctree:: + :maxdepth: 1 + :caption: Performance Showcase + + show/index + +.. toctree:: + :maxdepth: 1 + :caption: Commercial Support + + support/index diff --git a/docs/en/quick_start/demo.rst b/docs/en/quick_start/demo.rst new file mode 100755 index 00000000..4168d870 --- /dev/null +++ b/docs/en/quick_start/demo.rst @@ -0,0 +1,313 @@ +Quick Verification Based on Existing Demos +============================================= + +Before learning USB or CherryUSB code, we need to quickly verify based on existing demos. Why? To enhance interest in USB and build confidence for the next steps. If demos can't run, or if you explore writing code by yourself, or read USB basic concepts first, you may find that you can't understand anything in the end - there are so many concepts that you simply can't remember them, thus losing interest in USB. Therefore, running demos first is very important. Below I will list the currently supported demo repositories. + +Based on Bouffalolab Series Chips (Official SDK Support) +-------------------------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/cherryusb_bouffalolab + - FOTG210 + - less than latest + +Based on HPMicro Series Chips (Official SDK Support) +----------------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/cherryusb_hpmicro + - CHIPIDEA + - less than latest + +Based on esp32s2/s3/p4 Series Chips (Official SDK Support) +------------------------------------------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/cherryusb_esp32 + - DWC2 + - less than latest + +Default demo uses component library installation form, can be searched at https://components.espressif.com/ for cherryusb + +ESP-Registry can refer to the official documentation, recommended to use vscode + esp-idf development environment. + +- ctrl + shift + p select ESP-IDF welcome interface, then select Component manager + +.. figure:: img/esp1.png + +- Find cherryusb and install + +.. figure:: img/esp2.png + +- Open menuconfig, and open cherryusb configuration, select host or device mode according to actual situation + +.. figure:: img/esp3.png +.. figure:: img/esp4.png + +Based on Phytium Series Chips (Official SDK Support) +------------------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://gitee.com/phytium_embedded/phytium-free-rtos-sdk + - PUSB2/XHCI + - equal to v1.4.0 + +Based on Essemi Series Chips (Official SDK Support) +------------------------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/cherryusb_es32 + - MUSB + - less than latest + +Based on Artinchip Series Chips (Official SDK Support) +------------------------------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://gitee.com/artinchip/luban-lite + - AIC/EHCI/OHCI + - less than latest + +Based on Kendryte canmv-k230 Chip (Official SDK Support) +--------------------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/k230_sdk + - DWC2 + - less than latest + +Based on NXP MCX Series Chips +------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/cherryusb_mcx https://github.com/RT-Thread/rt-thread/tree/master/bsp/nxp/mcx + - CHIPIDEA/kinetis + - less than latest + +Based on SiFli SF32 Series Chips (Official SDK Support) +-------------------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/OpenSiFli/SiFli-SDK + - MUSB + - less than latest + +Based on RP2040/RP2035 Chips (Official SDK Support Coming Soon) +-------------------------------------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/pico-examples https://github.com/CherryUSB/pico-sdk + - RP2040 + - less than latest + +Based on Actionstech Series Chips (Official SDK Support) +----------------------------------------------------------- + +Not opensource, please contact to Actionstech official + +Based on ST Series Chips +--------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/cherryusb_stm32 + - DWC2/FSDEV + - less than latest + +Default demo projects provided: + +- F103 uses fsdev ip +- F429 host and device use USB1, pins pb14/pb15, default device does not enable DMA mode +- H7 device uses USB0, pins pa11/pa12, DMA mode not enabled. Host uses USB1, pins pb14/pb15, and needs nocache processing + +Demo provides **stm32xxx.ioc** file, double click to open, click **Generate Code**. + +.. caution:: After generation, please use git reset function to restore the overwritten `main.c` and `stm32xxx_it.c` files, prohibit being overwritten by cubemx. + +Covers F1/F4/H7, other chips are basically similar and won't be repeated. Specific differences are: + +- usb ip difference: F1 uses fsdev, F4/H7 use dwc2 +- dwc2 ip difference: USB0 (pins PA11/PA12) and USB1 (pins PB14/PB15), where USB1 defaults to full-speed, can connect external PHY to form high-speed host, and has DMA functionality +- F4 has no cache, H7 has cache + +If it's STM32F7/STM32H7 with cache functionality, you need to locate the ram used by usb to the no cache ram area. Example as follows + +.. code-block:: C + + cpu_mpu_config(0, MPU_Normal_NonCache, 0x24070000, MPU_REGION_SIZE_64KB); + +Corresponding sct script modification in Keil: + +.. code-block:: C + + LR_IROM1 0x08000000 0x00200000 { ; load region size_region + ER_IROM1 0x08000000 0x00200000 { ; load address = execution address + *.o (RESET, +First) + *(InRoot$$Sections) + .ANY (+RO) + .ANY (+XO) + } + RW_IRAM2 0x24000000 0x00070000 { ; RW data + .ANY (+RW +ZI) + } + USB_NOCACHERAM 0x24070000 0x00010000 { ; RW data + *(.noncacheable) + } + } + +USB Device Porting Points +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +- Use **stm32cubemx** to create project, configure basic RCC, UART (used as log) + +.. figure:: img/stm32_1.png +.. figure:: img/stm32_2.png + +- If using fsdev ip, check **USB**. If using dwc2 ip, check **USB_OTG_FS** or **USB_OTG_HS**. Enable USB interrupt. Other configurations are useless to us, no ST USB library will be used in the code. + +.. figure:: img/stm32_3_1.png +.. figure:: img/stm32_3_2.png + +- Configure usb clock to 48M + +.. figure:: img/stm32_4_1.png +.. figure:: img/stm32_4_2.png + +- Select project, here we choose keil, set stack and heap properly. If using msc, it's recommended to set them larger, then click **Generate Code**. + +.. figure:: img/stm32_5.png + +- Add CherryUSB required source code (**usbd_core.c**, **dwc2/usb_dc_dwc2.c** or **fsdev/usb_dc_fsdev.c**), as well as the class drivers you want to use. You can add corresponding class templates for convenient testing. + +.. figure:: img/stm32_6.png + +- Add necessary header files + +.. figure:: img/stm32_7.png + +- Copy **cherryusb_config_template.h**, place it in the `Core/Inc` directory, and name it `usb_config.h` + +.. figure:: img/stm32_8.png + +- If using fsdev ip, (starting from V1.5.0, need to add **fsdev/usb_glue_st.c**) implement the following macro definition in `usb_config.h`. The specific value varies for different chips: + +.. code-block:: C + + #define CONFIG_USBDEV_FSDEV_PMA_ACCESS 2 + +- Compiler recommends using **AC6**. Check **Microlib**, and implement **printf** for convenient log viewing later. + +.. figure:: img/stm32_10.png +.. figure:: img/stm32_11.png + +.. note :: Starting from V1.5.0, the following two steps are no longer needed because they are already implemented in **fsdev/usb_glue_st.c** and **dwc2/usb_glue_st.c** files + +- Copy the content of **HAL_PCD_MspInit** function in **xxx_msp.c** to **usb_dc_low_level_init** function, disable ST generated USB initialization + +.. figure:: img/stm32_12.png +.. figure:: img/stm32_14.png + +- Call `USBD_IRQHandler` in interrupt function and pass in `busid` + +.. figure:: img/stm32_13.png + +- If the chip has cache, please refer to :ref:`usb_cache` chapter for cache modification + +- Call template content initialization and fill in `busid` and USB IP's `reg base`. `busid` starts from 0 and cannot exceed `CONFIG_USBDEV_MAX_BUS` + +.. figure:: img/stm32_15.png + +USB Host Porting Points +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +The first 6 steps are the same as device side. Note that host driver only supports HS port with DMA (pins PB14/PB15), so FS port (pins PA11/PA12) is not supported (what's the point of a host without DMA). + +- Add CherryUSB required source code (**usbh_core.c**, **usbh_hub.c**, **usb_hc_dwc2.c**, **usb_glue_st.c** and adapter layer files in **osal** directory), as well as the class drivers you want to use, and you can add corresponding **usb host.c** for convenient testing. + +.. figure:: img/stm32_16.png + +- Compiler recommends using **AC6**. Check **Microlib**, and implement **printf** for convenient log viewing later. + +.. figure:: img/stm32_10.png +.. figure:: img/stm32_11.png + +- Copy **cherryusb_config_template.h**, place it in the `Core/Inc` directory, and name it `usb_config.h` + +.. note :: Starting from V1.5.0, the following two steps are no longer needed because they are already implemented in **fsdev/usb_glue_st.c** and **dwc2/usb_glue_st.c** files + +- Copy the content of `HAL_HCD_MspInit` function in **xxx_msp.c** to `usb_hc_low_level_init` function, disable ST generated USB initialization +- Call `USBH_IRQHandler` in interrupt function and pass in `busid` + +.. figure:: img/stm32_19.png + +- For linker script modifications, refer to :ref:`usbh_link_script` chapter +- If the chip has cache, please refer to :ref:`usb_cache` chapter for cache modification +- Call `usbh_initialize` and fill in `busid` and USB IP's `reg base` and `event_handler` (can be omitted as NULL). `busid` starts from 0 and cannot exceed `CONFIG_USBHOST_MAX_BUS` +- Start thread + +.. figure:: img/stm32_18.png diff --git a/docs/en/quick_start/img/env0.png b/docs/en/quick_start/img/env0.png new file mode 100755 index 00000000..c0a8b03f Binary files /dev/null and b/docs/en/quick_start/img/env0.png differ diff --git a/docs/en/quick_start/img/env1.png b/docs/en/quick_start/img/env1.png new file mode 100755 index 00000000..2a68e052 Binary files /dev/null and b/docs/en/quick_start/img/env1.png differ diff --git a/docs/en/quick_start/img/env2.png b/docs/en/quick_start/img/env2.png new file mode 100755 index 00000000..ee37101a Binary files /dev/null and b/docs/en/quick_start/img/env2.png differ diff --git a/docs/en/quick_start/img/esp1.png b/docs/en/quick_start/img/esp1.png new file mode 100755 index 00000000..1f059e71 Binary files /dev/null and b/docs/en/quick_start/img/esp1.png differ diff --git a/docs/en/quick_start/img/esp2.png b/docs/en/quick_start/img/esp2.png new file mode 100755 index 00000000..fd20e9ce Binary files /dev/null and b/docs/en/quick_start/img/esp2.png differ diff --git a/docs/en/quick_start/img/esp3.png b/docs/en/quick_start/img/esp3.png new file mode 100755 index 00000000..82a7162f Binary files /dev/null and b/docs/en/quick_start/img/esp3.png differ diff --git a/docs/en/quick_start/img/esp4.png b/docs/en/quick_start/img/esp4.png new file mode 100755 index 00000000..ffb2882a Binary files /dev/null and b/docs/en/quick_start/img/esp4.png differ diff --git a/docs/en/quick_start/img/question1.png b/docs/en/quick_start/img/question1.png new file mode 100755 index 00000000..a852e6aa Binary files /dev/null and b/docs/en/quick_start/img/question1.png differ diff --git a/docs/en/quick_start/img/question2.png b/docs/en/quick_start/img/question2.png new file mode 100755 index 00000000..e00b3bfa Binary files /dev/null and b/docs/en/quick_start/img/question2.png differ diff --git a/docs/en/quick_start/img/stm32_1.png b/docs/en/quick_start/img/stm32_1.png new file mode 100755 index 00000000..b91044a5 Binary files /dev/null and b/docs/en/quick_start/img/stm32_1.png differ diff --git a/docs/en/quick_start/img/stm32_10.png b/docs/en/quick_start/img/stm32_10.png new file mode 100755 index 00000000..d55b38e7 Binary files /dev/null and b/docs/en/quick_start/img/stm32_10.png differ diff --git a/docs/en/quick_start/img/stm32_11.png b/docs/en/quick_start/img/stm32_11.png new file mode 100755 index 00000000..3ad5b074 Binary files /dev/null and b/docs/en/quick_start/img/stm32_11.png differ diff --git a/docs/en/quick_start/img/stm32_12.png b/docs/en/quick_start/img/stm32_12.png new file mode 100755 index 00000000..84aaffe8 Binary files /dev/null and b/docs/en/quick_start/img/stm32_12.png differ diff --git a/docs/en/quick_start/img/stm32_13.png b/docs/en/quick_start/img/stm32_13.png new file mode 100755 index 00000000..f12fad75 Binary files /dev/null and b/docs/en/quick_start/img/stm32_13.png differ diff --git a/docs/en/quick_start/img/stm32_14.png b/docs/en/quick_start/img/stm32_14.png new file mode 100755 index 00000000..e5aa5b19 Binary files /dev/null and b/docs/en/quick_start/img/stm32_14.png differ diff --git a/docs/en/quick_start/img/stm32_15.png b/docs/en/quick_start/img/stm32_15.png new file mode 100755 index 00000000..7c293287 Binary files /dev/null and b/docs/en/quick_start/img/stm32_15.png differ diff --git a/docs/en/quick_start/img/stm32_16.png b/docs/en/quick_start/img/stm32_16.png new file mode 100755 index 00000000..70f2e63c Binary files /dev/null and b/docs/en/quick_start/img/stm32_16.png differ diff --git a/docs/en/quick_start/img/stm32_18.png b/docs/en/quick_start/img/stm32_18.png new file mode 100755 index 00000000..456df189 Binary files /dev/null and b/docs/en/quick_start/img/stm32_18.png differ diff --git a/docs/en/quick_start/img/stm32_19.png b/docs/en/quick_start/img/stm32_19.png new file mode 100755 index 00000000..a796dc75 Binary files /dev/null and b/docs/en/quick_start/img/stm32_19.png differ diff --git a/docs/en/quick_start/img/stm32_2.png b/docs/en/quick_start/img/stm32_2.png new file mode 100755 index 00000000..671b1b82 Binary files /dev/null and b/docs/en/quick_start/img/stm32_2.png differ diff --git a/docs/en/quick_start/img/stm32_3_1.png b/docs/en/quick_start/img/stm32_3_1.png new file mode 100755 index 00000000..9e42196d Binary files /dev/null and b/docs/en/quick_start/img/stm32_3_1.png differ diff --git a/docs/en/quick_start/img/stm32_3_2.png b/docs/en/quick_start/img/stm32_3_2.png new file mode 100755 index 00000000..492d6739 Binary files /dev/null and b/docs/en/quick_start/img/stm32_3_2.png differ diff --git a/docs/en/quick_start/img/stm32_4_1.png b/docs/en/quick_start/img/stm32_4_1.png new file mode 100755 index 00000000..e81437bc Binary files /dev/null and b/docs/en/quick_start/img/stm32_4_1.png differ diff --git a/docs/en/quick_start/img/stm32_4_2.png b/docs/en/quick_start/img/stm32_4_2.png new file mode 100755 index 00000000..dd90f5b8 Binary files /dev/null and b/docs/en/quick_start/img/stm32_4_2.png differ diff --git a/docs/en/quick_start/img/stm32_5.png b/docs/en/quick_start/img/stm32_5.png new file mode 100755 index 00000000..5bec9878 Binary files /dev/null and b/docs/en/quick_start/img/stm32_5.png differ diff --git a/docs/en/quick_start/img/stm32_6.png b/docs/en/quick_start/img/stm32_6.png new file mode 100755 index 00000000..f0ad9a0b Binary files /dev/null and b/docs/en/quick_start/img/stm32_6.png differ diff --git a/docs/en/quick_start/img/stm32_7.png b/docs/en/quick_start/img/stm32_7.png new file mode 100755 index 00000000..8aef0bfa Binary files /dev/null and b/docs/en/quick_start/img/stm32_7.png differ diff --git a/docs/en/quick_start/img/stm32_8.png b/docs/en/quick_start/img/stm32_8.png new file mode 100755 index 00000000..08d2e724 Binary files /dev/null and b/docs/en/quick_start/img/stm32_8.png differ diff --git a/docs/en/quick_start/migration.rst b/docs/en/quick_start/migration.rst new file mode 100755 index 00000000..2ea61df7 --- /dev/null +++ b/docs/en/quick_start/migration.rst @@ -0,0 +1,62 @@ +Partial Changes Migration Guide +====================================== + +usbh_initialize +------------------ + +usbh_initialize has added event_handler parameter starting from v1.6.0. Usually not needed, can pass NULL. + +dwc2 glue st +---------------- + +Starting from v1.5.0, dwc2 glue file has built-in low-level initialization, such as `usb_dc_low_level_init`, which depends on `HAL_PCD_MspInit` and `HAL_HCD_MspInit`. Must use stm32cubemx generation. Third-party platforms do not guarantee having these function implementations, check by yourself. + + +dwc2 glue +---------------- + +Starting from v1.5.1, dwc2 adds `struct dwc2_user_params` for implementing different configurations for multiple dwc2 ports. It replaces `usbd_get_dwc2_gccfg_conf` and `usbh_get_dwc2_hccfg_conf` functions, +and adds `dwc2_get_user_params` function implementation, example as follows: + +.. code-block:: C + + #ifndef CONFIG_USB_DWC2_CUSTOM_PARAM + void dwc2_get_user_params(uint32_t reg_base, struct dwc2_user_params *params) + { + memcpy(params, ¶m_common, sizeof(struct dwc2_user_params)); + #ifdef CONFIG_USB_DWC2_CUSTOM_FIFO + struct usb_dwc2_user_fifo_config s_dwc2_fifo_config; + + dwc2_get_user_fifo_config(reg_base, &s_dwc2_fifo_config); + + params->device_rx_fifo_size = s_dwc2_fifo_config.device_rx_fifo_size; + for (uint8_t i = 0; i < MAX_EPS_CHANNELS; i++) { + params->device_tx_fifo_size[i] = s_dwc2_fifo_config.device_tx_fifo_size[i]; + } + #endif + } + #endif + +host serial +---------------- + +Starting from v1.6.0, host adds host serial framework for unifying all serial-like devices. The following APIs need to be replaced with new serial APIs: + +.. code-block:: C + + int usbh_xxx_set_line_coding(struct usbh_xxx *xxx_class, struct cdc_line_coding *line_coding); + int usbh_xxx_get_line_coding(struct usbh_xxx *xxx_class, struct cdc_line_coding *line_coding); + int usbh_xxx_set_line_state(struct usbh_xxx *xxx_class, bool dtr, bool rts); + + int usbh_xxx_bulk_in_transfer(struct usbh_xxx *xxx_class, uint8_t *buffer, uint32_t buflen, uint32_t timeout); + int usbh_xxx_bulk_out_transfer(struct usbh_xxx *xxx_class, uint8_t *buffer, uint32_t buflen, uint32_t timeout); + +Replace with: + +.. code-block:: C + + struct usbh_serial *usbh_serial_open(const char *devname, uint32_t open_flags); + int usbh_serial_close(struct usbh_serial *serial); + int usbh_serial_control(struct usbh_serial *serial, int cmd, void *arg); + int usbh_serial_write(struct usbh_serial *serial, const void *buffer, uint32_t buflen); + int usbh_serial_read(struct usbh_serial *serial, void *buffer, uint32_t buflen); diff --git a/docs/en/quick_start/opensource.rst b/docs/en/quick_start/opensource.rst new file mode 100755 index 00000000..ed8af520 --- /dev/null +++ b/docs/en/quick_start/opensource.rst @@ -0,0 +1,61 @@ +Official Open Source Project Sharing +========================================= + +In addition to basic vendor SDK support, we have also supported some popular open source projects to help developers better use these projects. Below are the adapted demo project links. For specific adaptation layers, refer to https://github.com/cherry-embedded/CherryUSB/tree/master/platform. + +DAPLINK +-------------- + +Adaptation link: https://github.com/cherry-embedded/CherryDAP + +Blackmagic +-------------- + +Adaptation link: https://github.com/zhangjiance/bmp-hpm-port + +RT-Thread +-------------- + +Adaptation link: https://github.com/RT-Thread/rt-thread + +NUTTX/VELA +-------------- + +Adaptation link: https://github.com/CherryUSB/cherryusb_nuttx + +Zephyr +-------------- + +Adaptation link: https://github.com/hpmicro/zephyr_sdk_glue + +Cangaroo +-------------- + +Cangaroo is an open source CAN bus analyzer software. We provide four-channel CANFD analyzer based on hpmicro hpm5361 + +Host computer adaptation link: https://github.com/RCSN/cangaroo_hpmicro_canfd_analyzer +Lower computer adaptation link: https://github.com/RCSN/hpm_sdk_extra/tree/main/demos/cangaroo_hpmicro + +LVGL +-------------- + +Adaptation link: https://github.com/cherry-embedded/CherryUSB/tree/master/platform/lvgl + +QMK +-------------- + +QMK is an open-source keyboard firmware for Atmel AVR and Arm USB families. + +Adaptation link: To be released + +Klipper +-------------- + +Klipper is a 3D-printer firmware. + +Adaptation link: To be released + +MAKCU/KMBOX +-------------- + +Those who know, know - not released \ No newline at end of file diff --git a/docs/en/quick_start/q&a.rst b/docs/en/quick_start/q&a.rst new file mode 100755 index 00000000..3780b578 --- /dev/null +++ b/docs/en/quick_start/q&a.rst @@ -0,0 +1,135 @@ +Q & A +============================================ + +Porting Question Template +------------------------------ + +Please submit questions through the following channels: +- RT-Thread Official Forum: https://club.rt-thread.org/ask/tag/5f5f851966917b14.html +- Github issue: https://github.com/cherry-embedded/CherryUSB/issues/new/choose + +Please include the following information in your question: + +- Version being used +- Board, pins, and USB IP being used +- Whether USB interrupts, USB clock, USB pins, USB PHY configuration are configured, and whether USB register addresses are correct (include screenshots) +- Whether USB interrupts are triggered +- Whether the chip has cache functionality and whether no-cache processing has been implemented (include screenshots) +- Whether USB circuit is drawn correctly, whether dupont wires are used for connection, whether direct connection is used; if normal, please explain why it's normal +- If interrupts can be triggered, configure **#define CONFIG_USB_DBG_LEVEL USB_DBG_LOG** and provide logs (limited to commercial IPs only; other IPs are prohibited from enabling logs, otherwise enumeration will fail) +- Whether the chip has been taped out and is being sold + +Other Question Template +-------------------------------- + +Specifically describe the phenomenon, reproduction method, test using my provided demo, and provide complete logs + +How Much Performance Can CherryUSB Achieve +---------------------------------------------------------------- + +Reference: :ref:`performace_show` + +ST IP Naming Issues +------------------------- + +ST naming uses USB_OTG_FS, USB_OTG_HS, which doesn't indicate whether it's actually high-speed or full-speed, but represents the maximum speed it can support (high-speed). Both are actually full-speed and require external high-speed PHY. Therefore, please avoid using these terms in questions; use USB0(PA11/PA12), USB1(PB14/PB15) instead. The same applies to other domestic manufacturers. + +GD IP Issues +------------------ + +GD IP uses DWC2, but all hardware parameters read are 0 (I don't understand why they don't want people to know). Therefore, users need to know the hardware information themselves. Starting from version 1.5.0, because hardware information needs to be read, it cannot be used directly. + +Additionally, GD cannot use the EPDIS function to close endpoints after reset. Users need to delete the following code from the reset interrupt: + +.. code-block:: C + + USB_OTG_INEP(i)->DIEPCTL = (USB_OTG_DIEPCTL_EPDIS | USB_OTG_DIEPCTL_SNAK); + USB_OTG_OUTEP(i)->DOEPCTL = (USB_OTG_DOEPCTL_EPDIS | USB_OTG_DOEPCTL_SNAK); + +There may also be other unknown bugs; please test yourself. + +Cannot enumerate after enabling USB_LOG_DBG +---------------------------------------------------------------- + +Only commercial IPs can enumerate after enabling, other IPs are prohibited from enabling, otherwise enumeration will fail. Those who know, know. + +Which version to use for USB3 CV testing +-------------------------------------------- + +Version 1.4.3 and above + +Ep addr XXX fifo overflow +------------------------------ + +.. figure:: img/question1.png + +This error indicates that the default FIFO space setting for this endpoint is insufficient and needs to be increased. This is commonly seen in DWC2/MUSB IP. Refer to relevant glue files for FIFO settings. + +Ep addr XXX overflow +------------------------------ + +.. figure:: img/question2.png + +This error indicates that the IP hardware doesn't have that many endpoints. Please change IP or reduce endpoint usage. +Of course, you can also modify to bidirectional endpoints. Considering that not all IPs support bidirectional endpoints, the default demo doesn't implement bidirectional functionality. For example, the default is 81 02 rather than 81 01. If supported, modify it yourself. Some IP bidirectional endpoints may occupy the same hardware information and may not be usable simultaneously, please check yourself. + +This dwc2 version does not support dma mode, so stop working +---------------------------------------------------------------- + +This DWC2 version doesn't support DMA mode, prohibited from use. Not using DMA mode will frequently trigger NAK interrupts (about every tens of microseconds), causing excessively high CPU usage. + +Which chips support OTG +------------------------------ + +Currently, only HPM chips support OTG functionality in the mainline, automatically switching between host/device modes via ID pin. For other chips, please use manual switching mode OR implement ID recognition driver yourself. + +How to change PC-recognized COM port name +---------------------------------------------------------------- + +This is a Microsoft CDC ACM driver issue that cannot be modified. If modification is needed, please contact Microsoft, pay fees, and write driver to make changes. + +Connect and disconnect events not triggering +---------------------------------------------------------------- + +Currently only HPM chips support connect and disconnect events. For other chips, please use USB VBUS detection circuit. DWC2 IP supports it, but because it requires pin usage and most are log ports, and different enabling configurations vary, support is not provided. + +__has_include error +------------------------------------------------------------------ +If error occurs, compiler needs to support C99 syntax. If using Keil, please use AC6 compiler. + +When to use CONFIG_USB_HS +---------------------------------------------------------------- + +Enable when your chip hardware supports high speed and you want to initialize in high-speed mode. Related IP will configure internal or external high-speed PHY based on this macro. + +Failed to enable port +---------------------------------------------------------------- + +Insufficient power supply or hardware USB circuit issues + +Porting USB host encounters URB return -12/-14 +---------------------------------------------------------------- + +Check PHY configuration, cache configuration (if any), power supply (recommend self-powered) + +USB_ERR_NAK explanation +---------------------------------------------------------------- + +USB_ERR_NAK only exists in DWC2 buffer DMA/slave mode (we don't use slave mode). DWC2 in buffer DMA mode doesn't support hardware handling of NAK interrupts for interrupt transfers, requiring software handling, resulting in very frequent NAK interrupts. Recommend using with timer. +DWC2 scatter/gather DMA mode is fully handled by hardware but doesn't support split transfers. In summary, **tasteless to eat, pity to discard**. + +USB host connecting USB network adapter issues +---------------------------------------------------------------- + +Manifests as network adapter recognition and IP address allocation but inability to ping. This is because the network adapter itself needs to enable auto-dial, usually requiring AT port settings. Specifically for EC20/ML307 modules. + +When to enable CONFIG_USB_DCACHE_ENABLE +------------------------------------------------- + +Enable this macro when chip has cache functionality and doesn't use no-cache RAM to ensure data consistency. **When using EHCI, nocache RAM is still needed internally**. Usually, for third-party platforms or components that don't use no-cache RAM macros but use global variables or malloc operations, this RAM typically goes through cache, requiring this macro. Recommend mandatory enabling for third-party platform usage. + +Which IPs have data alignment requirements +------------------------------------------------- + +- When CONFIG_USB_DCACHE_ENABLE is not enabled, only DWC2/WCH/AIC IP requires 4-byte alignment, others need only 1-byte alignment. +- When CONFIG_USB_DCACHE_ENABLE is enabled, all IPs need alignment to CONFIG_USB_ALIGN_SIZE bytes \ No newline at end of file diff --git a/docs/en/quick_start/rtthread.rst b/docs/en/quick_start/rtthread.rst new file mode 100755 index 00000000..d01f2673 --- /dev/null +++ b/docs/en/quick_start/rtthread.rst @@ -0,0 +1,62 @@ +RT-Thread Software Package Development Guide +============================================= + +.. note:: CherryUSB has been added to the RT-Thread mainline and you can choose to use the mainline version with the same configuration method. + +This section mainly introduces using the software package manager provided by RT-Thread to configure projects, demonstrated with env. The operations in this section are the same for different chips and won't be repeated later. After opening env, use menuconfig to enter the package manager and select CherryUSB in the path shown in the figure. + +.. figure:: img/env0.png + +Device Configuration +-------------------------- + +* Select Enable USB device mode and press Enter to enter. +* The first configuration is to configure USB speed, divided into **FS, HS**, indicating whether to use full-speed or high-speed functionality. High-speed functionality requires built-in high-speed PHY or external PHY +* The second configuration is to select the USB device IP. If you are not sure which IP your chip uses, refer to the README in the corresponding `port` directory. +* Select the class you want to use +* Choose whether to use a demo template + +.. figure:: img/env1.png + +* Finally exit and save. +* Copy `cherryusb_config_template.h` file to your project directory, rename it to `usb_config.h`, add the corresponding header file path, and modify the following content: + +.. code-block:: C + + #include "rtthread.h" + + #define CONFIG_USB_PRINTF(...) rt_kprintf(__VA_ARGS__) + +* USB IP related config needs to be modified by the user according to the actual chip situation +* Implement the `usb_dc_low_level_init` function in code +* Call `USBD_IRQHandler` in the USB interrupt function and pass in `busid` +* Call `usbd_initialize` and fill in `busid` and USB IP's `reg base`. `busid` starts from 0 and cannot exceed `CONFIG_USBDEV_MAX_BUS` +* Use `scons --target=mdk5` or `scons` to compile. If using mdk, you need to use the AC6 compiler +* If the chip has cache, refer to the :ref:`usb_cache` chapter for cache modifications + +Host Configuration +-------------------------- + +* Select Enable usb host mode and press Enter +* Select USB host ip. If you're not sure which ip your chip uses, refer to the readme under the corresponding **port** directory +* Check class drivers as needed +* Choose whether to enable template demo, recommended not to use + +.. figure:: img/env2.png + +* Finally exit and save. +* Copy `cherryusb_config_template.h` file to your project directory, rename it to `usb_config.h`, add the corresponding header file path, and implement the following content: + +.. code-block:: C + + #include "rtthread.h" + + #define CONFIG_USB_PRINTF(...) rt_kprintf(__VA_ARGS__) + +* USB IP related config needs to be modified by the user according to the actual chip situation +* Implement the `usb_hc_low_level_init` function in code +* Call `USBH_IRQHandler` in the USB interrupt function and pass in `busid` +* Call `usbh_initialize` and fill in `busid` and USB IP's `reg base` and `event_handler` (can be omitted as NULL). `busid` starts from 0 and cannot exceed `CONFIG_USBHOST_MAX_BUS` +* Use `scons --target=mdk5` or `scons` to compile. If using mdk, you need to use the AC6 compiler +* For linker script modifications, refer to the :ref:`usbh_link_script` chapter +* If the chip has cache, refer to the :ref:`usb_cache` chapter for cache modifications diff --git a/docs/en/quick_start/share.rst b/docs/en/quick_start/share.rst new file mode 100755 index 00000000..e4ebdae8 --- /dev/null +++ b/docs/en/quick_start/share.rst @@ -0,0 +1,27 @@ +Developer Experience/Open Source Project Sharing +==================================================== + +- `RT-Thread-CherryUSB - RT-Thread `_ + +- `[HPM-DIY]hpm6750 USB开源协议栈性能对比-cherryusb or tinyusb? `_ + +- `RT-Thread-CherryUSB移植笔记(一):APM32F407VGT6 DWC2移植 Port.A Full-Speed + Por.B High-SpeedRT-Thread问答社区 - RT-Thread `_ + +- `华大HC32F460XXX移植cherryusb协议栈,实现USB CDC ACM_cherryusb移植教程-CSDN博客 `_ + +- `rt-thread使用cherryusb实现虚拟串口-CSDN博客 `_ + +- `F1C100S+rtt+CherryUSB的USB HOST成功读到U盘 / 全志 SOC / WhyCan Forum(哇酷开发者社区) `_ + +- `模仿stm32标准库风格写的库文件(f1c100s/f1c200s),且已移植了rt-thread、lvgl、fatfs、cherryusb / 全志 SOC / WhyCan Forum(哇酷开发者社区) `_ + +- `printalyzer-timer: F-Stop enlarging timer and print exposure meter `_ + +- `MiSTeryNano: Atari STE MiSTery core for the Tang Nano 20k FPGA `_ + +- `Cherryuf2 `_ + +- `PicoPiFi: Driverless RNDIS USB WIFI Dongle `_ + +- `phobia: Phobia Motor Controller `_ + diff --git a/docs/en/quick_start/start.rst b/docs/en/quick_start/start.rst new file mode 100755 index 00000000..a19ffe4a --- /dev/null +++ b/docs/en/quick_start/start.rst @@ -0,0 +1,52 @@ +Getting Started Guide +========================= + +First of all, welcome to the world of USB. Here you can learn various USB knowledge and CherryUSB porting, usage, advanced features, etc. However, as a newcomer, you must be quite confused because USB is difficult (actually, once you learn CherryUSB, you'll find that USB is not difficult at all). So in this situation, what should your learning path be? Here, I recommend following my learning path, as this will be most helpful for your USB growth and you won't give up midway. + +First, don't start by looking at concepts. There's an ancient saying: **"What you read on paper is always shallow; to truly understand, you must practice"**. Just looking at written materials won't teach you much. Only when you practice yourself can you gain deeper understanding of these concepts. So as a beginner, what should you do? Please follow these steps. + + +Step 1 +------------- + +You need to have learned C language, UART, and DMA - these are the basics. If you haven't learned them, please go learn them first, otherwise you'll struggle. You might ask: what's the relationship between USB and UART/DMA? I can only say two words: **equivalent**. + +Step 2 +------------- + +Download demo projects and get them running. **For slow learners, I recommend using the same chip model as the demo**. For fast learners, you can choose to port to supported chip models yourself. If you can't even get the demos running, what USB can you learn? Don't you agree? + +Step 3 +--------- + +Excellent! By this step, you can already skillfully port and run all examples. So what should you learn next? **Transactions**, **Requests**, and **Descriptors** (in your USB learning journey, you only need to know these three things; you don't need to know anything else). + +Step 4 +---------- + +First, we need to know that USB transactions include SETUP/IN/OUT, which are essentially equivalent to sending commands, sending data, and receiving data - very simple. As for the control phase, data phase, and status phase that you hear about in online discussions about enumeration, they are not transactions themselves; they are just multiple transactions representing a phase. + +Step 5 +---------- + +Then look at the **USB Enumeration** section and learn about the concept of **descriptors**. At this point, you can briefly look at what descriptors are and what types exist. You need to remember and memorize **the composition of device, configuration, interface, and endpoint descriptors**. You don't need to know anything else because everything else is fixed and can be copy-pasted later. There are enumeration captures for various devices in the group files that you can download and review. + +Step 6 +---------- + +Then you can look at what **requests** are, the composition of request structures, and what types of requests exist - just a basic understanding will suffice. Why? Because it's just an 8-byte data format. Everyone can write UART + custom protocol, and USB requests are the same, just predefined. + +Step 7 +---------- + +At this point, you should familiarize yourself with some protocol stack APIs by referring to the **API Manual** section. You also need to know what conditions constitute interrupt completion, when reception is considered complete, and when transmission is considered complete. You can refer to the **USB Knowledge Extension** section. + +Step 8 +---------- + +By this step, you're definitely very knowledgeable, and you can start working on some small functional projects. During this period, please repeatedly review the **USB Knowledge Extension** section until you truly understand it, because this content is very important and will affect the execution results of our code. + +Step 9 +---------- + +You've reached this point - you shouldn't need me anymore! Now you can look at USB concepts, USB details, and CherryUSB code flow. Then it's just consolidation, consolidation, and more consolidation. Congratulations, you've graduated! diff --git a/docs/en/quick_start/transplant.rst b/docs/en/quick_start/transplant.rst new file mode 100755 index 00000000..eefb0a7a --- /dev/null +++ b/docs/en/quick_start/transplant.rst @@ -0,0 +1,137 @@ +General Chip Porting Guide +======================================= + +This section mainly introduces the general steps and precautions for porting CherryUSB host and device protocol stacks to all chips with USB IP. Before porting, you need to **prepare a basic project that can print helloworld**. Default printing uses `printf`. If it's host mode, **you need to prepare a basic project that can execute OS scheduling normally**. + +USB Device Porting Key Points +------------------------------------- + +- Copy CherryUSB source code to the project directory and add source files and header file paths as needed. It's recommended to add all header file paths. Among them, `usbd_core.c` and `usb_dc_xxx.c` are required items. `usb_dc_xxx.c` is the USB IP DCD driver corresponding to the chip. If you don't know which USB IP your chip belongs to, refer to the readme of different USB IPs under the **port** directory. If the USB IP you're using is not supported, you'll have to implement it yourself +- Copy `cherryusb_config_template.h` file to your project directory, rename it to `usb_config.h`, and add the corresponding directory header file path +- Implement `usb_dc_low_level_init` function (this function is mainly responsible for USB clock, pin, and interrupt initialization). This function can be placed in any C file that participates in compilation. For USB clock, pin, interrupt initialization, please add them yourself according to the source code provided by your chip manufacturer. +- Call `USBD_IRQHandler` in the interrupt function and pass `busid`. If `USBD_IRQHandler` already exists in the interrupt entry of your SDK, please change the name in the USB protocol stack +- If the chip has cache, refer to the :ref:`usb_cache` section for cache modifications +- Register descriptors and call `usbd_initialize`, fill in `busid` and USB IP's `reg base`. `busid` starts from 0 and cannot exceed `CONFIG_USBDEV_MAX_BUS`. You can directly use templates under the demo directory + +USB Host Porting Key Points +------------------------------------- + +- Copy CherryUSB source code to project directory and add source files and header file paths as needed. It's recommended to add all header file paths. Among them, `usbh_core.c`, `usb_hc_xxx.c` and source files under the **osal** directory (choose corresponding source files according to different OS) are required. `usb_hc_xxx.c` is the USB IP HCD driver corresponding to the chip. If you don't know which USB IP your chip belongs to, refer to the readme of different USB IPs under the **port** directory. If the USB IP you're using is not supported, you'll have to implement it yourself +- Copy `cherryusb_config_template.h` file to your project directory, rename it to `usb_config.h`, and add the corresponding directory header file path +- Implement `usb_hc_low_level_init` function (this function is mainly responsible for USB clock, pin, and interrupt initialization). This function can be placed in any C file that participates in compilation. For USB clock, pin, interrupt initialization, please add them yourself according to the source code provided by your chip manufacturer. +- Call `usbh_initialize` and fill in `busid`, USB IP's `reg base`, and `event_handler` (can be omitted as NULL). `busid` starts from 0 and cannot exceed `CONFIG_USBHOST_MAX_BUS` +- Call `USBH_IRQHandler` in the interrupt function and pass `busid`. If `USBH_IRQHandler` already exists in the interrupt entry of your SDK, please change the name in the USB protocol stack +- Refer to the :ref:`usbh_link_script` section for linker script modifications +- If the chip has cache, refer to the :ref:`usb_cache` section for cache modifications +- Call `usbh_initialize`, fill in `busid`, USB IP's `reg base`, and `event_handler` (can be omitted as NULL). `busid` starts from 0 and cannot exceed `CONFIG_USBHOST_MAX_BUS`. For basic CDC + HID + MSC, refer to the `usb_host.c` file. For others, refer to adaptations under the **platform** directory + +.. _usbh_link_script: + +Host Linker Script Modifications +------------------------------------- + +When using the host, if you haven't modified the linker script, you will encounter `__usbh_class_info_start__` and `__usbh_class_info_end__` undefined errors. This is because the host protocol stack requires adding a section to the linker script to store class information. + +- No modification needed if using KEIL + +- If using GCC, add the following code to the linker script (needs to be placed in flash location, recommended at the end): + +.. code-block:: C + + // Add the following code to the ld file + . = ALIGN(4); + __usbh_class_info_start__ = .; + KEEP(*(.usbh_class_info)) + __usbh_class_info_end__ = .; + +GCC example: + +.. code-block:: C + + /* The program code and other data into "FLASH" Rom type memory */ + .text : + { + . = ALIGN(4); + *(.text) /* .text sections (code) */ + *(.text*) /* .text* sections (code) */ + *(.glue_7) /* glue arm to thumb code */ + *(.glue_7t) /* glue thumb to arm code */ + *(.eh_frame) + + KEEP (*(.init)) + KEEP (*(.fini)) + . = ALIGN(4); + __usbh_class_info_start__ = .; + KEEP(*(.usbh_class_info)) + __usbh_class_info_end__ = .; + . = ALIGN(4); + _etext = .; /* define a global symbols at end of code */ + } > FLASH + +- Segger Embedded Studio example: + +.. code-block:: C + + define block cherryusb_usbh_class_info { section .usbh_class_info }; + + define exported symbol __usbh_class_info_start__ = start of block cherryusb_usbh_class_info; + define exported symbol __usbh_class_info_end__ = end of block cherryusb_usbh_class_info + 1; + + place in AXI_SRAM { block cherryusb_usbh_class_info }; + keep { section .usbh_class_info}; + + +.. _usb_cache: + +cache Configuration Modification +-------------------------------------- + +For chips with cache functionality, the protocol stack and port will not clean or invalidate RAM in the cache region, so a non-cache RAM area needs to be used for maintenance. +`USB_NOCACHE_RAM_SECTION` macro specifies variables to be placed in non-cache RAM. By default, `USB_NOCACHE_RAM_SECTION` is defined as `__attribute__((section(".noncacheable")))`. +Therefore, users need to add a no cache RAM section in the corresponding linker script, and the section must include `.noncacheable`. + +.. note:: Note that just modifying the nocache section in the linker script is not sufficient. You also need to configure the RAM in that section to be truly nocache, which typically requires configuring MPU attributes (for ARM, refer to the stm32h7 demo). + +GCC: + +.. code-block:: C + + MEMORY + { + RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 256K - 64K + RAM_nocache (xrw) : ORIGIN = 0x20030000, LENGTH = 64K + FLASH (rx) : ORIGIN = 0x8000000, LENGTH = 512K + } + + ._nocache_ram : + { + . = ALIGN(4); + *(.noncacheable) + } >RAM_nocache + + +SCT: + +.. code-block:: C + + LR_IROM1 0x08000000 0x00200000 { ; load region size_region + ER_IROM1 0x08000000 0x00200000 { ; load address = execution address + *.o (RESET, +First) + *(InRoot$$Sections) + .ANY (+RO) + .ANY (+XO) + } + RW_IRAM2 0x24000000 0x00070000 { ; RW data + .ANY (+RW +ZI) + } + USB_NOCACHERAM 0x24070000 0x00010000 { ; RW data + *(.noncacheable) + } + } + +ICF: + +.. code-block:: C + + define region NONCACHEABLE_RAM = [from 0x1140000 size 256K]; + place in NONCACHEABLE_RAM { section .noncacheable, section .noncacheable.init, section .noncacheable.bss }; // Noncacheable diff --git a/docs/en/show/img/usbdev_msc.png b/docs/en/show/img/usbdev_msc.png new file mode 100755 index 00000000..30f22383 Binary files /dev/null and b/docs/en/show/img/usbdev_msc.png differ diff --git a/docs/en/show/img/usbdev_rndis_linux.png b/docs/en/show/img/usbdev_rndis_linux.png new file mode 100755 index 00000000..94b97312 Binary files /dev/null and b/docs/en/show/img/usbdev_rndis_linux.png differ diff --git a/docs/en/show/img/usbdev_rndis_lwip.png b/docs/en/show/img/usbdev_rndis_lwip.png new file mode 100755 index 00000000..f4cfd0b3 Binary files /dev/null and b/docs/en/show/img/usbdev_rndis_lwip.png differ diff --git a/docs/en/show/img/usbdev_rndis_lwip2.png b/docs/en/show/img/usbdev_rndis_lwip2.png new file mode 100755 index 00000000..3fde91f9 Binary files /dev/null and b/docs/en/show/img/usbdev_rndis_lwip2.png differ diff --git a/docs/en/show/img/usbdev_rndis_wifi.png b/docs/en/show/img/usbdev_rndis_wifi.png new file mode 100755 index 00000000..d6817876 Binary files /dev/null and b/docs/en/show/img/usbdev_rndis_wifi.png differ diff --git a/docs/en/show/img/usbdev_rndis_wifi2.png b/docs/en/show/img/usbdev_rndis_wifi2.png new file mode 100755 index 00000000..dba9f3dd Binary files /dev/null and b/docs/en/show/img/usbdev_rndis_wifi2.png differ diff --git a/docs/en/show/img/usbdev_rndis_win.png b/docs/en/show/img/usbdev_rndis_win.png new file mode 100755 index 00000000..5293023a Binary files /dev/null and b/docs/en/show/img/usbdev_rndis_win.png differ diff --git a/docs/en/show/img/usbdev_uvc_mjpeg.png b/docs/en/show/img/usbdev_uvc_mjpeg.png new file mode 100755 index 00000000..a2321c15 Binary files /dev/null and b/docs/en/show/img/usbdev_uvc_mjpeg.png differ diff --git a/docs/en/show/img/usbdev_uvc_yuv.png b/docs/en/show/img/usbdev_uvc_yuv.png new file mode 100755 index 00000000..a630cd67 Binary files /dev/null and b/docs/en/show/img/usbdev_uvc_yuv.png differ diff --git a/docs/en/show/img/usbhost_ax88772_1.png b/docs/en/show/img/usbhost_ax88772_1.png new file mode 100755 index 00000000..a267b292 Binary files /dev/null and b/docs/en/show/img/usbhost_ax88772_1.png differ diff --git a/docs/en/show/img/usbhost_ax88772_2.png b/docs/en/show/img/usbhost_ax88772_2.png new file mode 100755 index 00000000..fc6e96fc Binary files /dev/null and b/docs/en/show/img/usbhost_ax88772_2.png differ diff --git a/docs/en/show/img/usbhost_hub.png b/docs/en/show/img/usbhost_hub.png new file mode 100755 index 00000000..011468c7 Binary files /dev/null and b/docs/en/show/img/usbhost_hub.png differ diff --git a/docs/en/show/img/usbhost_hub2.png b/docs/en/show/img/usbhost_hub2.png new file mode 100755 index 00000000..00c09d6f Binary files /dev/null and b/docs/en/show/img/usbhost_hub2.png differ diff --git a/docs/en/show/img/usbhost_msc.png b/docs/en/show/img/usbhost_msc.png new file mode 100755 index 00000000..ec546a8d Binary files /dev/null and b/docs/en/show/img/usbhost_msc.png differ diff --git a/docs/en/show/img/usbhost_msc_xhci.png b/docs/en/show/img/usbhost_msc_xhci.png new file mode 100755 index 00000000..084250f2 Binary files /dev/null and b/docs/en/show/img/usbhost_msc_xhci.png differ diff --git a/docs/en/show/img/usbhost_rndis.png b/docs/en/show/img/usbhost_rndis.png new file mode 100755 index 00000000..12ab1a4e Binary files /dev/null and b/docs/en/show/img/usbhost_rndis.png differ diff --git a/docs/en/show/img/usbhost_uvc.gif b/docs/en/show/img/usbhost_uvc.gif new file mode 100755 index 00000000..c4df04e0 Binary files /dev/null and b/docs/en/show/img/usbhost_uvc.gif differ diff --git a/docs/en/show/img/usbhost_wifi.png b/docs/en/show/img/usbhost_wifi.png new file mode 100755 index 00000000..e57fd85b Binary files /dev/null and b/docs/en/show/img/usbhost_wifi.png differ diff --git a/docs/en/show/index.rst b/docs/en/show/index.rst new file mode 100755 index 00000000..2e8d4417 --- /dev/null +++ b/docs/en/show/index.rst @@ -0,0 +1,103 @@ +.. _performace_show: + +Performance Showcase +============================================ + +The following demonstrates the performance of CherryUSB in different applications. Mainly demonstrates high-speed mode, as full-speed shows no significant performance difference. + +CDC ACM Communication +----------------------- + +Can achieve hardware limit performance. Of course, the hardware needs to theoretically support this speed, and CherryUSB supports it accordingly. Examples are as follows: + +- HPM Series (Device can reach 42MB/S, Host 44MB/S, already reached hardware limit) +- BL Series (Device 32MB/S, Host 25MB/S, already reached hardware limit) +- STM32F4 Full-speed (Device 900KB/S, Host 1.12MB/S, already reached hardware limit) + +Device speed test demo: cdc_acm_template.c with log disabled, script uses `tools/test_srcipts/test_cdc_speed.py` +Host speed test demo: usb_host.c with TEST_USBH_CDC_SPEED=1 + +USB Device MSC +----------------- + +Demonstrates USB Device MSC using SDXC3.0 + EMMC testing. + +.. figure:: img/usbdev_msc.png + +USB Device RNDIS +----------------------- + +.. note:: By default, RNDIS only supports single packets, so the speeds below are minimum speeds. Multi-packet support requires contacting the author. + +Demonstrates USB Device RNDIS speed in LAN with lwip. + +As client + +.. figure:: img/usbdev_rndis_lwip.png + +As server + +.. figure:: img/usbdev_rndis_lwip2.png + +Demonstrates USB Device RNDIS + WIFI passthrough testing. + +.. figure:: img/usbdev_rndis_wifi.png +.. figure:: img/usbdev_rndis_wifi2.png + +Demonstrates USB Device RNDIS + 100Mbps Ethernet passthrough testing. + +.. figure:: img/usbdev_rndis_win.png +.. figure:: img/usbdev_rndis_linux.png + +USB Device UVC +----------------------- + +Demonstrates USB Device UVC + camera transmission of YUYV/MJPEG 640 * 480 images. 30 FPS. + +.. figure:: img/usbdev_uvc_mjpeg.png +.. figure:: img/usbdev_uvc_yuv.png + +USB Host HUB +----------------------- + +Multi-level hub support, demonstrates 1-to-7 HUB. + +.. figure:: img/usbhost_hub.png +.. figure:: img/usbhost_hub2.png + +USB Host MSC +----------------------- + +Demonstrates USB Host MSC speed under USB2.0 and USB3.0. Solid-state USB drives are recommended for testing. + +.. figure:: img/usbhost_msc.png +.. figure:: img/usbhost_msc_xhci.png + +USB Host UVC +----------------------- + +Demonstrates USB Host UVC driving 648 * 480 YUV camera. 30 FPS. + +.. figure:: img/usbhost_uvc.gif + +USB Host ASIX Network Card +------------------------------------------------- + +Demonstrates USB Host driving AX88772 USB Ethernet module. + +.. figure:: img/usbhost_ax88772_1.png +.. figure:: img/usbhost_ax88772_2.png + +USB Host RNDIS Network Card +------------------------------------------------- + +Demonstrates USB Host driving mobile phone. Enable USB network sharing on the phone to use RNDIS. + +.. figure:: img/usbhost_rndis.png + +USB Host WIFI +----------------------- + +Demonstrates USB Host driving BL616 USB WIFI. + +.. figure:: img/usbhost_wifi.png diff --git a/docs/en/support/img/dwc2_hostuac.png b/docs/en/support/img/dwc2_hostuac.png new file mode 100755 index 00000000..6050f531 Binary files /dev/null and b/docs/en/support/img/dwc2_hostuac.png differ diff --git a/docs/en/support/img/dwc2_hostuvc1.png b/docs/en/support/img/dwc2_hostuvc1.png new file mode 100755 index 00000000..70b4dd1a Binary files /dev/null and b/docs/en/support/img/dwc2_hostuvc1.png differ diff --git a/docs/en/support/img/dwc2_hostuvc2.png b/docs/en/support/img/dwc2_hostuvc2.png new file mode 100755 index 00000000..8885e90e Binary files /dev/null and b/docs/en/support/img/dwc2_hostuvc2.png differ diff --git a/docs/en/support/img/dwc2_hostuvc3.png b/docs/en/support/img/dwc2_hostuvc3.png new file mode 100755 index 00000000..fb3e1eef Binary files /dev/null and b/docs/en/support/img/dwc2_hostuvc3.png differ diff --git a/docs/en/support/img/ehci_hostuvc1.png b/docs/en/support/img/ehci_hostuvc1.png new file mode 100755 index 00000000..2bd6590a Binary files /dev/null and b/docs/en/support/img/ehci_hostuvc1.png differ diff --git a/docs/en/support/img/ehci_hostuvc2.png b/docs/en/support/img/ehci_hostuvc2.png new file mode 100755 index 00000000..f44fa68c Binary files /dev/null and b/docs/en/support/img/ehci_hostuvc2.png differ diff --git a/docs/en/support/img/mtpdev.png b/docs/en/support/img/mtpdev.png new file mode 100755 index 00000000..513b8ac9 Binary files /dev/null and b/docs/en/support/img/mtpdev.png differ diff --git a/docs/en/support/img/ohci.png b/docs/en/support/img/ohci.png new file mode 100755 index 00000000..171f77be Binary files /dev/null and b/docs/en/support/img/ohci.png differ diff --git a/docs/en/support/img/rndisrx.png b/docs/en/support/img/rndisrx.png new file mode 100755 index 00000000..ce1133ed Binary files /dev/null and b/docs/en/support/img/rndisrx.png differ diff --git a/docs/en/support/img/rndistx.png b/docs/en/support/img/rndistx.png new file mode 100755 index 00000000..69e45db8 Binary files /dev/null and b/docs/en/support/img/rndistx.png differ diff --git a/docs/en/support/img/tmcdev1.png b/docs/en/support/img/tmcdev1.png new file mode 100755 index 00000000..1eaf7155 Binary files /dev/null and b/docs/en/support/img/tmcdev1.png differ diff --git a/docs/en/support/img/tmcdev2.png b/docs/en/support/img/tmcdev2.png new file mode 100755 index 00000000..97c8297b Binary files /dev/null and b/docs/en/support/img/tmcdev2.png differ diff --git a/docs/en/support/img/usbhost_uvc.gif b/docs/en/support/img/usbhost_uvc.gif new file mode 100755 index 00000000..c4df04e0 Binary files /dev/null and b/docs/en/support/img/usbhost_uvc.gif differ diff --git a/docs/en/support/index.rst b/docs/en/support/index.rst new file mode 100755 index 00000000..cc49dc4a --- /dev/null +++ b/docs/en/support/index.rst @@ -0,0 +1,43 @@ +Commercial Support +============================================ + +The following content is commercially charged. For support, please email 1203593632@qq.com. + +- OHCI Driver + +.. figure:: img/ohci.png + +- ISO driver and UAC/UVC framework in EHCI IP, used with host UVC & UAC classes (this part is open source). ISO supports 1/2/3 packets per microframe, supports MJPEG and YUV cameras + +.. figure:: img/ehci_hostuvc1.png +.. figure:: img/ehci_hostuvc2.png + +Demonstrates USB Host UVC driver with 648 * 480 YUV camera. FPS 30. + +.. figure:: img/usbhost_uvc.gif + +- ISO driver and UAC/UVC framework in DWC2 IP, used with host UVC & UAC classes (this part is open source). ISO supports 1/2/3 packets per microframe, supports MJPEG and YUV cameras + +.. figure:: img/dwc2_hostuvc1.png +.. figure:: img/dwc2_hostuvc2.png +.. figure:: img/dwc2_hostuvc3.png +.. figure:: img/dwc2_hostuac.png + +- ISO driver and UAC/UVC framework in MUSB IP, used with host UVC & UAC classes (this part is open source). MUSB requires standard IP specified by Mentor Graphics company + +- Device MTP class driver, supports multiple files and folders, supports MCU-side file addition/deletion and synchronization with PC + +.. figure:: img/mtpdev.png + +- Device TMC class driver + +.. figure:: img/tmcdev1.png +.. figure:: img/tmcdev2.png + +- USB network class high-performance version optimization, includes CDC-NCM, CDC-RNDIS, proprietary class drivers (supports multi-packet transmission and reception), RNDIS example shown below + +.. figure:: img/rndistx.png +.. figure:: img/rndisrx.png + +- Customized class driver or IP driver adaptation +- Technical support services \ No newline at end of file diff --git a/docs/en/tools/img/chrytool1.png b/docs/en/tools/img/chrytool1.png new file mode 100755 index 00000000..8717316a Binary files /dev/null and b/docs/en/tools/img/chrytool1.png differ diff --git a/docs/en/tools/img/chrytool2.png b/docs/en/tools/img/chrytool2.png new file mode 100755 index 00000000..a0eb4192 Binary files /dev/null and b/docs/en/tools/img/chrytool2.png differ diff --git a/docs/en/tools/img/chrytool3.png b/docs/en/tools/img/chrytool3.png new file mode 100755 index 00000000..52a3556b Binary files /dev/null and b/docs/en/tools/img/chrytool3.png differ diff --git a/docs/en/tools/img/chrytool4.png b/docs/en/tools/img/chrytool4.png new file mode 100755 index 00000000..8ad68400 Binary files /dev/null and b/docs/en/tools/img/chrytool4.png differ diff --git a/docs/en/tools/img/chrytool5.png b/docs/en/tools/img/chrytool5.png new file mode 100755 index 00000000..17849324 Binary files /dev/null and b/docs/en/tools/img/chrytool5.png differ diff --git a/docs/en/tools/img/chrytool6.png b/docs/en/tools/img/chrytool6.png new file mode 100755 index 00000000..931ccad8 Binary files /dev/null and b/docs/en/tools/img/chrytool6.png differ diff --git a/docs/en/tools/img/chrytool7.png b/docs/en/tools/img/chrytool7.png new file mode 100755 index 00000000..283a7fc9 Binary files /dev/null and b/docs/en/tools/img/chrytool7.png differ diff --git a/docs/en/tools/index.rst b/docs/en/tools/index.rst new file mode 100755 index 00000000..f6728b62 --- /dev/null +++ b/docs/en/tools/index.rst @@ -0,0 +1,49 @@ +chryusb_configurator +-------------------------- + +`chryusb_configurator `_ mainly serves to generate descriptor arrays when using the device protocol stack, which are then registered using `usbd_desc_register`. + +- First, we download chryusb_configurator.exe from GitHub, then install it all the way through. Then double-click to open it, click `Project`, and click `New Project` + +.. figure:: img/chrytool1.png + +- After creation, default descriptor configuration will be generated, including **Device Descriptor**, **Configuration Descriptor**, **String Descriptor**, and **String Descriptor** supports three by default + +.. figure:: img/chrytool2.png + +- Then we can modify the information of related descriptors as needed, such as VID and PID in **Device Descriptor**, class parameters, **Power** in **Configuration Descriptor**, etc. + +- Then for class addition, you need to click `File` and click `New File` + +.. figure:: img/chrytool3.png + +- Then the right side provides some class descriptor templates. Select one for initialization + +.. figure:: img/chrytool4.png + +- If there are multiple classes, repeat the above two steps + +- Then we modify the parameters of related endpoints as needed, such as direction, address, size, interval + +.. figure:: img/chrytool5.png + +- Finally click `File` and save the file with extension `.chry` +- Switch to the project file with extension `.chrybase`, then click `Add Group Configuration` to import the just configured class file + +.. figure:: img/chrytool6.png + +- Click `Project` and click `Save Project` +- Click `Compile` to generate descriptor arrays + +.. figure:: img/chrytool7.png + +- Copy the compiled files to your own project for use + +Lecroy USB Protocol Suite +-------------------------- + +Wireshark +-------------------------- + +Audacity +-------------------------- diff --git a/docs/en/usb/img/1.png b/docs/en/usb/img/1.png new file mode 100755 index 00000000..e85ddf7a Binary files /dev/null and b/docs/en/usb/img/1.png differ diff --git a/docs/en/usb/img/10.png b/docs/en/usb/img/10.png new file mode 100755 index 00000000..bb57645e Binary files /dev/null and b/docs/en/usb/img/10.png differ diff --git a/docs/en/usb/img/11.png b/docs/en/usb/img/11.png new file mode 100755 index 00000000..11056e33 Binary files /dev/null and b/docs/en/usb/img/11.png differ diff --git a/docs/en/usb/img/12.png b/docs/en/usb/img/12.png new file mode 100755 index 00000000..4149d81e Binary files /dev/null and b/docs/en/usb/img/12.png differ diff --git a/docs/en/usb/img/13.png b/docs/en/usb/img/13.png new file mode 100755 index 00000000..29a544b2 Binary files /dev/null and b/docs/en/usb/img/13.png differ diff --git a/docs/en/usb/img/14.png b/docs/en/usb/img/14.png new file mode 100755 index 00000000..8ca094a4 Binary files /dev/null and b/docs/en/usb/img/14.png differ diff --git a/docs/en/usb/img/15.png b/docs/en/usb/img/15.png new file mode 100755 index 00000000..eba7b89b Binary files /dev/null and b/docs/en/usb/img/15.png differ diff --git a/docs/en/usb/img/16.png b/docs/en/usb/img/16.png new file mode 100755 index 00000000..259336ca Binary files /dev/null and b/docs/en/usb/img/16.png differ diff --git a/docs/en/usb/img/17.png b/docs/en/usb/img/17.png new file mode 100755 index 00000000..c42de390 Binary files /dev/null and b/docs/en/usb/img/17.png differ diff --git a/docs/en/usb/img/18.png b/docs/en/usb/img/18.png new file mode 100755 index 00000000..f08b6354 Binary files /dev/null and b/docs/en/usb/img/18.png differ diff --git a/docs/en/usb/img/19.png b/docs/en/usb/img/19.png new file mode 100755 index 00000000..2e6eb9ce Binary files /dev/null and b/docs/en/usb/img/19.png differ diff --git a/docs/en/usb/img/2.png b/docs/en/usb/img/2.png new file mode 100755 index 00000000..5b4f5f20 Binary files /dev/null and b/docs/en/usb/img/2.png differ diff --git a/docs/en/usb/img/20.png b/docs/en/usb/img/20.png new file mode 100755 index 00000000..a44898a8 Binary files /dev/null and b/docs/en/usb/img/20.png differ diff --git a/docs/en/usb/img/21.png b/docs/en/usb/img/21.png new file mode 100755 index 00000000..7aa81e95 Binary files /dev/null and b/docs/en/usb/img/21.png differ diff --git a/docs/en/usb/img/22.png b/docs/en/usb/img/22.png new file mode 100755 index 00000000..370d39f9 Binary files /dev/null and b/docs/en/usb/img/22.png differ diff --git a/docs/en/usb/img/23.png b/docs/en/usb/img/23.png new file mode 100755 index 00000000..e08db16e Binary files /dev/null and b/docs/en/usb/img/23.png differ diff --git a/docs/en/usb/img/24.png b/docs/en/usb/img/24.png new file mode 100755 index 00000000..fec98d49 Binary files /dev/null and b/docs/en/usb/img/24.png differ diff --git a/docs/en/usb/img/25.png b/docs/en/usb/img/25.png new file mode 100755 index 00000000..9bcaf151 Binary files /dev/null and b/docs/en/usb/img/25.png differ diff --git a/docs/en/usb/img/26.png b/docs/en/usb/img/26.png new file mode 100755 index 00000000..d439b7c4 Binary files /dev/null and b/docs/en/usb/img/26.png differ diff --git a/docs/en/usb/img/27.png b/docs/en/usb/img/27.png new file mode 100755 index 00000000..1047da1b Binary files /dev/null and b/docs/en/usb/img/27.png differ diff --git a/docs/en/usb/img/28.png b/docs/en/usb/img/28.png new file mode 100755 index 00000000..95b760c5 Binary files /dev/null and b/docs/en/usb/img/28.png differ diff --git a/docs/en/usb/img/29.png b/docs/en/usb/img/29.png new file mode 100755 index 00000000..09538d16 Binary files /dev/null and b/docs/en/usb/img/29.png differ diff --git a/docs/en/usb/img/3.png b/docs/en/usb/img/3.png new file mode 100755 index 00000000..b8ef0823 Binary files /dev/null and b/docs/en/usb/img/3.png differ diff --git a/docs/en/usb/img/30.png b/docs/en/usb/img/30.png new file mode 100755 index 00000000..d3014f95 Binary files /dev/null and b/docs/en/usb/img/30.png differ diff --git a/docs/en/usb/img/4.png b/docs/en/usb/img/4.png new file mode 100755 index 00000000..f80c5366 Binary files /dev/null and b/docs/en/usb/img/4.png differ diff --git a/docs/en/usb/img/5.png b/docs/en/usb/img/5.png new file mode 100755 index 00000000..ec6a4ba2 Binary files /dev/null and b/docs/en/usb/img/5.png differ diff --git a/docs/en/usb/img/6.png b/docs/en/usb/img/6.png new file mode 100755 index 00000000..2d280398 Binary files /dev/null and b/docs/en/usb/img/6.png differ diff --git a/docs/en/usb/img/7.png b/docs/en/usb/img/7.png new file mode 100755 index 00000000..e7562f11 Binary files /dev/null and b/docs/en/usb/img/7.png differ diff --git a/docs/en/usb/img/8.png b/docs/en/usb/img/8.png new file mode 100755 index 00000000..a4ac6ad4 Binary files /dev/null and b/docs/en/usb/img/8.png differ diff --git a/docs/en/usb/img/9.png b/docs/en/usb/img/9.png new file mode 100755 index 00000000..a8b5b2a3 Binary files /dev/null and b/docs/en/usb/img/9.png differ diff --git a/docs/en/usb/img/overview1.png b/docs/en/usb/img/overview1.png new file mode 100755 index 00000000..fbaf5a19 Binary files /dev/null and b/docs/en/usb/img/overview1.png differ diff --git a/docs/en/usb/img/overview2.png b/docs/en/usb/img/overview2.png new file mode 100755 index 00000000..c8b3b779 Binary files /dev/null and b/docs/en/usb/img/overview2.png differ diff --git a/docs/en/usb/img/usb_enum.png b/docs/en/usb/img/usb_enum.png new file mode 100755 index 00000000..01c67c15 Binary files /dev/null and b/docs/en/usb/img/usb_enum.png differ diff --git a/docs/en/usb/img/usb_request.png b/docs/en/usb/img/usb_request.png new file mode 100755 index 00000000..bb9f2637 Binary files /dev/null and b/docs/en/usb/img/usb_request.png differ diff --git a/docs/en/usb/img/usbstruct.png b/docs/en/usb/img/usbstruct.png new file mode 100755 index 00000000..bd062ca3 Binary files /dev/null and b/docs/en/usb/img/usbstruct.png differ diff --git a/docs/en/usb/usb2.0_basic.rst b/docs/en/usb/usb2.0_basic.rst new file mode 100755 index 00000000..76dca6d2 --- /dev/null +++ b/docs/en/usb/usb2.0_basic.rst @@ -0,0 +1,294 @@ +USB Basic Concepts (2.0 Focus) +========================================= + +This document mainly explains Chapters 5, 7, 8, and 9 provided in the official USB manual `usb2.0.pdf `_. +If you are a beginner to USB, it's recommended not to read this section first, but to get the example demos running and become familiar with usage before reading. + +Introduction +----------------- + +What is USB? What is it used for? What are its advantages? You can search for these online, so I won't mention them. Let me first talk about USB interfaces and speed classifications according to different USB versions, as shown in the figure: + +.. figure:: img/overview1.png + +Next is the voltage level standard that USB needs to meet. With the voltage level standard, the signal states mentioned below can be classified. The voltage ranges and maximum currents supported by USB2.0 and USB3.0 are as follows: + +.. figure:: img/overview2.png + +USB Signal States +--------------------- + +First, we need to understand the Signaling Level in USB electrical characteristics, which refers to signal states. USB mainly relies on D+ and D- to achieve different signal states for communication. The official manual section 7.1.7 lists the requirements that D+ and D- need to meet for signal states corresponding to low-speed, full-speed, and high-speed operations. + +.. figure:: img/1.png +.. figure:: img/2.png +.. figure:: img/3.png + +- **Differential 0 and Differential 1**: These two states are used for general data communication through USB. When the D+ line is high and the D- line is low, this state is differential 1. When the D+ line is low and the D- line is high, this state is differential 0. +- **J State and K State**: In addition to differential signals, the USB specification also defines two other differential states: J state and K state. Their definitions are determined by device speed. On full-speed and high-speed devices, J state is differential 1 and K state is differential 0. On low-speed devices, this situation is reversed. +- **Single-Ended 0 (SE0)**: The state that occurs when both D+ and D- are at low level. This state indicates a reset, disconnection, or end of a data packet. +- **Single-Ended 1 (SE1)**: The state that occurs when both D+ and D- are at high level. This state is not intentionally generated and should not appear in USB design. +- **Idle**: A state that must occur before and after sending a data packet. If one data line is at low level and the other data line is at high level, it indicates an idle state. The definition of high and low levels is determined by the device speed. On full-speed devices, the idle state means D+ is high and D- is low. On low-speed devices, this situation is reversed. +- **Resume**: Used to wake up a device from suspended state. This operation is achieved by sending a K state. +- **Start of Packet (SOP)**: When the D+ and D- lines transition from idle state to K state, this will occur before starting a low-speed or full-speed data packet. +- **End of Packet (EOP)**: Occurs at the end of a low-speed or full-speed data packet. EOP occurs when the SE0 state lasts for two bit times (bit time will be introduced later) and the J state lasts for 1 bit time. +- **Reset**: Occurs when the SE0 state lasts for 10 ms. After SE0 lasts for at least 2.5 ms, the device will reset and begin entering the reset state. +- **Keep Alive**: A signal used in low-speed devices. Low-speed devices lack a start-of-frame packet (used to prevent suspended state). Every 1 ms, they use an EOP to prevent the device from entering suspended state. + +.. note:: It should be noted that for low-speed devices, the J and K states and differential 0/1 are opposite to those of full-speed/high-speed devices. + +Below, we use a waveform to distinguish these signal states: + +.. figure:: img/4.png + +- In the first red box, we can see the start of a data packet. Assuming this is a full-speed device, D+ is high and D- is low, which is an idle state. +- In the second red box, D+ is low and D- is high, indicating a K state. The transition from idle to K state indicates this is an SOP. +- Starting from the third red box represents data, showing JKJKJKJKJK. +- The fourth red box represents SE0, because both D+ and D- are at low level. +- In the fifth red box, after SE0 lasted for a period of time, it became D+ high and D- low, indicating it is a J state. The transition from SE0 to J state indicates this is an EOP. + +USB Speed Detection +------------------------- + +How is USB speed determined? This is described in manual section 7.1.5.1. USB speed detection mainly relies on 1.5K pull-up resistors on D+ and D- lines. If D+ has a 1.5k pull-up, the device is a full-speed device. If D- has a 1.5k pull-up, it is a low-speed device. High-speed devices initially appear as full-speed devices, with a 1.5k pull-up resistor on the D+ line just like full-speed devices. The USB2.0 hub treats it as a full-speed device. Subsequently, the hub and device confirm each other's identity through a series of handshake signals, ultimately determining the device as high-speed. + +.. figure:: img/5.png + +USB Connection and Disconnection Detection +--------------------------------------------- + +So when we plug our device into a USB host, how does the host know that a device has been inserted or removed? Manual section 7.1.7.3 provides the answer, as shown in the figure: + +.. figure:: img/6.png +.. figure:: img/7.png + +First is connection detection. The host detects that a data line level has been pulled high and maintained for a period of time, and considers that a device has been connected. When a low-speed device connects, the host will detect that the D- line is pulled high. When a full-speed/high-speed device connects, the host will detect that the D+ line is pulled high. +For disconnection detection, the pull-down resistors on the D+ and D- data lines on the host side take effect. After disconnection, both lines are at low level. When the low level persists for TDDIS time, it will be considered a disconnected state by the host. In the above figure, TDDIS is between 2 and 2.5us. + +USB Power +--------------------- + +As USB power, USB devices can be divided into two device types: bus-powered and self-powered. + +- Bus power is an advantage of USB design. Since devices are powered through the bus, they do not need to use bulky internal or external power supplies and can still maintain their own operation. The bus can be powered by the host or hub. When using a bus-powered device, users must consider its power consumption before configuring the device to a certain state. +- Self-powered devices power themselves by using external power sources (such as DC power adapters or batteries). Self-powered devices need to consider some precautions during the design process. The USB specification requires self-powered devices to continuously monitor their own VBUS line. During the time when VBUS is not present, the device must disconnect the power supplied to the pull-up resistors on the D+/D- lines, thereby preventing power supply to the host or hub. Otherwise, it will cause USB compliance testing to fail. However, self-powered hubs can obtain up to 100 mA of current from the bus. + +USB Device States +--------------------- + +At the moment when a USB device is plugged into the host, the device state of the USB device itself will change. This device state, as we will learn later in the enumeration process, actually describes the enumeration process. This part is described in manual section 9.1.1. + +.. figure:: img/9.png + +- **Attached**: This state occurs when a device is plugged into the host/hub, but the host/hub is not supplying power to the VBUS line. It usually occurs when the hub detects an overcurrent event. Although the device is still connected, the host has removed the power supply to it. +- **Powered**: A device is connected to USB and receiving power, but has not yet received a reset request. +- **Default**: A device is connected to USB, receiving power, and has been reset by the host. At this time, the device has no device address and will respond to address 0. +- **Address**: A device is connected to USB, receiving power, has been reset, and has a unique address. However, the device is still not configured. +- **Configured**: The device is connected to USB, receiving power, has been reset, has a unique address, and is configured, but has not yet entered suspended state. At this time, bus-powered devices can consume more than 100 mA of current. +- **Suspended**: As described above, the device has established connection and is configured, but will not perform any bus operations within 3 ms. + +The diagram translated into English is: + +.. figure:: img/10.png + +USB Encoding and Bit Stuffing +----------------------------------- + +First, USB data is transmitted serially, just like UART, I2C, SPI, etc. Continuous 01 signals are sent to the receiver through only one data line. However, because the sender and receiver operate at different frequencies, signal synchronization becomes an issue. For example, when the receiver receives a low level that lasts for a period of time, it cannot determine whether this represents 5 zeros or 1000 zeros. One solution is to add a clock signal while transmitting the data signal to synchronize transmission at both ends. The receiver samples the data signal with the assistance of the clock signal to correctly parse the transmitted data. I2C does this, with SDA transmitting data and SCL transmitting the synchronization clock: + +.. figure:: img/11.png + +Although this solves the problem, it requires an additional clock signal line to transmit the clock. Since USB has no clock signal, is there a way to maintain synchronization at both ends without needing an additional clock signal? +Yes, this is RZ encoding (Return-to-zero Code), also called return-to-zero encoding. + +RZ Encoding (Return-to-zero Code) +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +RZ encoding (Return-to-zero Code) is also called return-to-zero encoding. In RZ encoding, positive level represents logic 1, negative level represents logic 0, and after each bit of data is transmitted, the signal returns to zero level. That is, three voltage levels appear on the signal line: positive level, negative level, and zero level. + +.. figure:: img/12.png + +As can be seen from the diagram, because each bit is reset to zero after transmission, the receiver only needs to sample after the signal is reset to zero, thus eliminating the need for a separate clock signal. In fact, RZ encoding is equivalent to encoding the clock signal into the data using a reset-to-zero method. Such a signal is also called a self-clocking signal. +While this saves on clock and data lines, it still has drawbacks because in RZ encoding, most of the data bandwidth is wasted on transmitting "return to zero". +NRZ Encoding (Non-return-to-zero Code) +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +Removing this return-to-zero step, NRZ encoding (Non-return-to-zero Code) emerged. The difference from RZ is that NRZ does not require return to zero. + +.. figure:: img/13.png + +NRZI Encoding (Non-Return-to-Zero Inverted Code) +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +The difference between NRZI encoding (Non-Return-to-Zero Inverted Code) and NRZ is that NRZI uses signal transitions to represent one logic and signal maintenance to represent another logic. This is described in manual section 7.1.8. + +.. figure:: img/14.png + +As shown in the figure, we can derive a simple memory method: when encountering a 0 edge, the level flips; when encountering a 1 edge, it remains unchanged. + +Bit Stuffing +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +However, there is still a problem. Although the receiver can actively match the sender's frequency, there will always be errors between them. If the data signal consists of 1000 logic 1s, after USB NRZI encoding, it becomes a very long period without level changes. In this situation, even if the receiver's frequency differs from the sender by one thousandth, it will cause the data to be sampled as 1001 or 999 ones. +USB's solution to this problem is forced bit insertion, also known as bit stuffing. If the data to be transmitted contains 6 consecutive 1s, a 0 is forcibly inserted after the 6th 1 before transmission, forcing the transmitted signal to transition and thereby forcing the receiver to adjust frequency. +The receiver only needs to delete the 0 after 6 consecutive 1s to restore the original data. This is described in manual section 7.1.9. + +.. figure:: img/15.png +.. figure:: img/16.png +.. figure:: img/17.png + +Before data is NRZI encoded, a zero is inserted after every six consecutive ones in the data stream to force transitions in the NRZI data stream, which gives the receiver logic at least one data transition every seven bits to ensure data and clock lock. Bit stuffing is enabled starting from sync pattern. The data "one" that ends the sync pattern is counted as the first "one" in the sequence. Transmitter bit stuffing is always enforced except during high-speed EOP. If required by bit stuffing rules, a zero bit will be inserted even if it is the last bit before the end of packet (EOP) signal. The receiver must decode NRZI data, identify stuffed bits, and discard them. + +.. caution:: The following content can be summarized in one diagram. Understanding it is sufficient; there is no need to memorize it. + +.. figure:: img/usbstruct.png + +USB Fields +--------------------- + +USB fields constitute the most basic and smallest unit in USB communication. Later packets and transactions are fundamentally composed of fields, while fields are composed of bits. The fields section is described in manual section 8.1. + +.. note:: USB's bit transmission mode follows the LSB-first principle. + +Sync Field +^^^^^^^^^^^^^^^^^^^^^^^^ + +In USB systems, the host and device do not share a clock, which makes it impossible for the receiver to accurately know when the sender is sending data. Although SOP can be detected, this is far from sufficient. Therefore, a sync field is needed to keep the receiver and sender synchronized during the transmission process, so every packet must start with a sync field. The sync field is 0x01, which after encoding becomes 10101000B. + +.. figure:: img/18.png + +Packet Identifier Field +^^^^^^^^^^^^^^^^^^^^^^^^ + +PID consists of a four-bit packet type field and a four-bit check field, occupying 8 bits, as shown in the figure. PID indicates the packet type and, by inference, the packet format and the type of error detection applied to the packet. The four-bit check field of PID is generated by performing a one's complement of the packet type field, ensuring reliable decoding of PID so that the rest of the packet can be correctly interpreted. If the four PID check bits are not the complement of their respective packet identifier bits, a PID error exists. + +.. figure:: img/19.png + +Since there are 4 bits, this means PID types can be divided into 16 types. These 16 types are further subdivided into 4 categories: Token PID, Data PID, Handshake PID, and Special PID. + +.. figure:: img/20.png + +Address Field +^^^^^^^^^^^^^^^^^^^^^^^^ + +The address field is divided into device address field and endpoint address field. The device address field occupies 7 bits. Excluding address 0, the host can allocate 127 addresses. + +.. figure:: img/21.png + +The endpoint address field occupies 4 bits, providing a total of 16 endpoints. + +.. figure:: img/22.png + +Frame Number Field +^^^^^^^^^^^^^^^^^^^^^^^^ + +The frame number field occupies 11 bits. Each time the host sends a frame, the frame number increases by 1, as shown in the figure. In high-speed devices, frames contain microframes. 1 frame = 8 microframes, and microframes increment by 0.1. The concepts of frames and microframes will be supplemented later. + +.. figure:: img/23.png + +Data Field +^^^^^^^^^^^^^^^^^^^^^^^^ + +Depending on the transmission type, the data length in the data field varies from 0-1024 bytes. + +.. figure:: img/24.png + +CRC Field +^^^^^^^^^^^^^^^^^^^^^^^^ + +Cyclic Redundancy Check (CRC) is used to protect all non-PID fields in token and data packets. PID is not included in the CRC check of packets containing CRC. All CRCs are generated on individual fields in the transmitter before bit stuffing is performed. Similarly, CRC is decoded in the receiver after stuffed bits are removed. Token and data packet CRCs provide 100% coverage for all single-bit and double-bit errors. CRC failure is considered to indicate that one or more protected fields have been corrupted and causes the receiver to ignore those fields and, in most cases, ignore the entire packet. + +.. figure:: img/24.png + +- Token CRC + +A five-bit CRC field is provided for tokens and covers the ADDR and ENDP fields of IN, SETUP, and OUT tokens or the timestamp field of SOF tokens. PING and SPLIT special tokens also include a five-bit CRC field. + +The generator polynomial is: G(X) = X^5 + X^2 + 1 +The binary bit pattern representing this polynomial is 00101B. If all token bits are received without error, the five-bit checksum at the receiver will be 01100B. + +- Data CRC + +Data CRC is a 16-bit polynomial applied to the data field of data packets. + +The generator polynomial is: G(X) = X^16 + X^15 + X^2 + 1 +The binary bit pattern representing this polynomial is 1000000000000101B. If all data and CRC bits are received without error, the 16-bit checksum will be 1000000000001101B. + +USB Packets +--------------------- + +Packets are composed of fields. According to PID type, packets are divided into four major categories: Token packets, Data packets, Handshake packets, and Special packets. This section is described in official section 8.4.1. + +.. figure:: img/25.png + +Including SOP, as shown in the figure, forms a complete packet. + +.. figure:: img/26.png + +Token Packets +^^^^^^^^^^^^^^^^^^^^^^^^ + +Token packets are divided into: SETUP, IN, OUT, SOF. Among them, SETUP, IN, and OUT have the same field composition, as shown: + +.. figure:: img/27.png + +- PID field: Defines the data transfer direction from USB host to USB device. +- ADDR field: Specifies the USB device address. +- ENDP field: Specifies the endpoint number for receiving data. +- CRC field: Performs cyclic redundancy check for ADDR and ENDP fields. + +SOF packet field composition, as shown: + +.. figure:: img/28.png + +- PID field: Defines the data transfer direction from USB host to USB device. +- Frame Number field: Specifies the frame number of USB transmission, which is 11 bits. +- CRC field: Performs cyclic redundancy check for ADDR and ENDP fields. + +Data Packets +^^^^^^^^^^^^^^^^^^^^^^^^ + +.. figure:: img/29.png + +- PID field: Used to specify different data packet types. Supports 4 types of data packets: DATA0, DATA1, DATA2, and MDATA. +- Data field: Contains the transmitted data. The data size depends on the data transfer type and user requirements. According to USB protocol specifications, for low-speed USB data transmission, the maximum length is 8 bytes; for full-speed USB data transmission, the maximum length is 1023 bytes; for high-speed USB data transmission, the maximum data length is 1024 bytes. +- CRC field: Uses 16-bit cyclic redundancy check to protect the data field. + +Handshake Packets +^^^^^^^^^^^^^^^^^^^^^^^^ + +Handshake packets consist of an 8-bit PID and are used at the end of data transmission to report the status of this data transmission. The handshake packet is followed by the EOP signal that marks the end of the entire transaction. + +.. figure:: img/30.png + +Special Packets +^^^^^^^^^^^^^^^^^^^^^^^^ + +USB Transactions +--------------------- + +There are three commonly used USB transactions: SETUP, IN, OUT. Except for control transfers which use three transactions, other transfers use two transactions. Special transactions are transactions that do not carry data. + +SETUP Transaction +^^^^^^^^^^^^^^^^^^^^^^^^ + +IN Transaction +^^^^^^^^^^^^^^^^^^^^^^^^ + +OUT Transaction +^^^^^^^^^^^^^^^^^^^^^^^^ + +Special Transaction +^^^^^^^^^^^^^^^^^^^^^^^^ + +USB Transfers +--------------------- + +Control Transfer +^^^^^^^^^^^^^^^^^^^^^^^^ + +Bulk Transfer +^^^^^^^^^^^^^^^^^^^^^^^^ + +Interrupt Transfer +^^^^^^^^^^^^^^^^^^^^^^^^ + +Isochronous Transfer +^^^^^^^^^^^^^^^^^^^^^^^^ diff --git a/docs/en/usb/usb3.0_basic.rst b/docs/en/usb/usb3.0_basic.rst new file mode 100755 index 00000000..ccd03d08 --- /dev/null +++ b/docs/en/usb/usb3.0_basic.rst @@ -0,0 +1,32 @@ +USB Basic Concepts (3.0 Focus) +========================================= + +Introduction +------------ + + + +Similarities and Differences with USB 2.0 +-------------------------- + + +Link Layer +-------------------- + +LCW +^^^^^^^^^^ + +Protocol Layer +-------------------- + +LMP +^^^^^^^^^^^^^^^^^^^^^^^^ + +TP +^^^^^^^^^^^^^^^^^^^^^^^^ + +DP +^^^^^^^^^^^^^^^^^^^^^^^^ + +ITP +^^^^^^^^^^^^^^^^^^^^^^^^ \ No newline at end of file diff --git a/docs/en/usb/usb_desc.rst b/docs/en/usb/usb_desc.rst new file mode 100755 index 00000000..e4014d5f --- /dev/null +++ b/docs/en/usb/usb_desc.rst @@ -0,0 +1,37 @@ +USB Descriptors +========================================= + +This section references the official USB 2.0 PDF section 9.5. + +Device Descriptor +------------------------------------------------------------ + +Configuration Descriptor +------------------------------------------------------------ + +Interface Descriptor +------------------------------------------------------------ + +Endpoint Descriptor +------------------------------------------------------------ + +String Descriptor +------------------------------------------------------------ + +Interface Association Descriptor +------------------------------------------------------------ + +Device Qualifier Descriptor +------------------------------------------------------------ + +Other Speed Descriptor +------------------------------------------------------------ + +BOS Descriptor +------------------------------------------------------------ + +SuperSpeed Endpoint Companion Descriptor +------------------------------------------------------------ + +Enhanced SuperSpeed Isochronous Endpoint Companion Descriptor +---------------------------------------------------------------------- diff --git a/docs/en/usb/usb_enum.rst b/docs/en/usb/usb_enum.rst new file mode 100755 index 00000000..45cf297c --- /dev/null +++ b/docs/en/usb/usb_enum.rst @@ -0,0 +1,22 @@ +USB Enumeration +========================================= + +After understanding USB device requests, we can learn about the entire enumeration process of USB devices and see how devices like serial ports, mice, and USB drives are enumerated. During enumeration, the host will send device requests to obtain relevant information (i.e., descriptors). For specific requests sent, refer to the diagram below. + +.. figure:: img/usb_enum.png + +- First, connect the device to the USB cable, then plug it into the computer +- After the device is plugged in, it powers up and enters a powered state +- The host detects device insertion through D+/D- +- Reset the device +- Host sends **Get Device Descriptor Request** +- Optional reset operation +- Host sends **Set Device Address Request** +- Host sends **Get Configuration Descriptor Request**, may be obtained multiple times, which doesn't matter +- Host sends **Get String Descriptor Request**, normally obtains 3 strings, and continues to obtain specified strings if they are specified in subsequent descriptors +- Host sends **Get Device Qualifier Descriptor Request**, used to obtain requests when the device operates at other speeds. If the device can only work in full-speed mode, it must reply with stall, and the protocol stack will definitely print this request to inform you that the device does not support this command. +- Host sends **Set Configuration Request**, configures device endpoints, usually based on the configuration in endpoint descriptors. +- Standard device requests end here +- Host loads corresponding supported class drivers based on interface descriptors. If the host doesn't support them, it will prompt that no driver is found for the device +- After loading is complete, begins executing related requests for that class +- Finally performs class data flow transmission \ No newline at end of file diff --git a/docs/en/usb/usb_ext.rst b/docs/en/usb/usb_ext.rst new file mode 100755 index 00000000..b2250437 --- /dev/null +++ b/docs/en/usb/usb_ext.rst @@ -0,0 +1,39 @@ +.. _usb_ext: + +USB Knowledge Extension +========================================= + +What is Packetization +------------------------- + +Due to USB protocol specifications defining the maximum length of each packet, when we send data that exceeds the maximum packet length, we need to send it in packets - this is packetization. For example, if EP MPS is 64 and data length is 129, USB will transmit in the form of 64 + 64 + 1. +For USB IP, packetization is divided into software packetization and hardware packetization. Software packetization means user code handles packetization itself - this type of IP generally uses FIFO because FIFO depth is limited. The second type +uses hardware packetization. This type of USB IP generally comes with DMA or descriptor DMA functionality, making this type of IP undoubtedly the most efficient. CherryUSB fully utilizes this point, enabling USB speed to reach its maximum. + +For software packetization, even if the transmission length is 16K at once, **it is internally handled through software packetization. In this case, the transmission length has no impact on speed improvement**. +For hardware packetization, the transmission length affects speed because hardware packetization is performed through DMA, **the larger the transmission length at one time, the higher the DMA efficiency and the faster the speed**. (Of course, although other protocol stacks use DMA, some code implementations still process one packet at a time, which is equivalent to not using it, and this is also a reason for low speed) + +What is a Short Packet +---------------------------- + +Based on what we discussed about packetization above, a short packet is the last packet in the packetization (and its length is less than EP MPS). For example, when sending 129 bytes of data, USB will transmit it in the form of 64 + 64 + 1, where the last packet is 1 byte, and this 1 byte is the short packet. + +What is ZLP +------------- + +ZLP, as the name suggests, is a Zero-Length Packet, which is a short packet with data length of 0. It's used by USB devices at the end of data transmission. If the data length is exactly a multiple of the maximum packet length, then a ZLP packet needs to be sent to inform the other party that data transmission has ended. + +.. caution:: ZLP functionality is limited to CONTROL and BULK transfers + +When is an Interrupt Considered Complete +-------------------------------------------- + +Device reception: The received length equals the set length; the last received packet is a short packet. +Device transmission: The transmitted length equals the set length. If the transmitted length is a multiple of EP MPS, **usually** a ZLP needs to be sent additionally (limited to control and bulk transfers). + +.. note:: For device reception and bulk transfers, the reception length is usually designed as EP MPS. The following three cases can be modified to multiple EP MPS: fixed length; custom protocol with length information (e.g., MSC); host manually sends ZLP or short packet (e.g., RNDIS) + +.. note:: For device transmission and bulk transfers, there is no limit on transmission length, but if it is a multiple of EP MPS, ZLP usually needs to be sent. Custom protocols do not need to send ZLP, such as MSC. + +Host reception: Same as device reception +Host transmission: The transmitted length equals the set length diff --git a/docs/en/usb/usb_request.rst b/docs/en/usb/usb_request.rst new file mode 100755 index 00000000..75b29c15 --- /dev/null +++ b/docs/en/usb/usb_request.rst @@ -0,0 +1,6 @@ +USB Device Requests +========================================= + +This section references official USB 2.0 PDF sections 9.3 and 9.4. + +.. figure:: img/usb_request.png diff --git a/docs/en/usbdev.svg b/docs/en/usbdev.svg new file mode 100755 index 00000000..8f787289 --- /dev/null +++ b/docs/en/usbdev.svg @@ -0,0 +1,4 @@ + + + +
usbd_desc_register
usbd_add_interface
usbd_add_endpoint
    struct usbd_tx_rx_msg tx_msg[16];
    struct usbd_tx_rx_msg rx_msg[16];
struct usbd_interface *intf[16];
usbd_initialize
USBD_IRQHandler
usbd_event_reset_handler
usbd_event_ep0_setup_complete_handler
usbd_event_ep_in_complete_handler
usbd_event_ep_out_complete_handler
usbd_setup_request_handler
tx_msg[ep & 0x7f].cb
rx_msg[ep & 0x7f].cb
usbd_event_ep0_in_complete_handler
tx_msg[ep & 0x7f].cb (ep != 0)
usbd_event_ep0_out_complete_handler
rx_msg[ep & 0x7f].cb (ep != 0)
usbd_standard_request_handler
usbd_class_request_handler
usbd_vendor_request_handler
\ No newline at end of file diff --git a/docs/en/usbhost.svg b/docs/en/usbhost.svg new file mode 100755 index 00000000..b7d537b5 --- /dev/null +++ b/docs/en/usbhost.svg @@ -0,0 +1,9 @@ +
usbh_initialize
usbh_initialize
usbh_hub_initialize
usbh_hub_initialize
usbh_roothub_register
usbh_roothub_register
create usbh_hub_thread
create usbh_hub_thread
usb_hc_init
usb_hc_init
usbh_roothub_thread_wakeup
usbh_roothub_thread_wakeup +
hub_int_complete_callback
hub_int_complete_callback +
wakeup
wakeup
wakeup
wakeup
usbh_enumerate
usbh_enumerate +
search all ports
search all ports
usbh_hub_events
usbh_hub_events +
CLASS_CONNECT
CLASS_CONNECT +
search all interface drivers
search all interface drivers
usbh_find_class_driver
usbh_find_class_driver +
if hub class?
if hub class?
usbh_int_urb_fill


usbh_submit_urb
usbh_int_urb_fill...
Class Register
Class Register +
USBH_IRQHandler
USBH_IRQHandler +
Viewer does not support full SVG 1.1
\ No newline at end of file diff --git a/docs/en/usbip/cdns2.rst b/docs/en/usbip/cdns2.rst new file mode 100755 index 00000000..88afc8d2 --- /dev/null +++ b/docs/en/usbip/cdns2.rst @@ -0,0 +1,2 @@ +CDNS2 +=============== diff --git a/docs/en/usbip/cdns3.rst b/docs/en/usbip/cdns3.rst new file mode 100755 index 00000000..c2132d1a --- /dev/null +++ b/docs/en/usbip/cdns3.rst @@ -0,0 +1,2 @@ +CDNS3 +=============== diff --git a/docs/en/usbip/chipidea.rst b/docs/en/usbip/chipidea.rst new file mode 100755 index 00000000..57c46ec0 --- /dev/null +++ b/docs/en/usbip/chipidea.rst @@ -0,0 +1,2 @@ +CHIPIDEA +================= \ No newline at end of file diff --git a/docs/en/usbip/dwc2.rst b/docs/en/usbip/dwc2.rst new file mode 100755 index 00000000..6c5a8c08 --- /dev/null +++ b/docs/en/usbip/dwc2.rst @@ -0,0 +1,2 @@ +DWC2 +================= \ No newline at end of file diff --git a/docs/en/usbip/dwc3.rst b/docs/en/usbip/dwc3.rst new file mode 100755 index 00000000..746bbee6 --- /dev/null +++ b/docs/en/usbip/dwc3.rst @@ -0,0 +1,2 @@ +DWC3 +=============== diff --git a/docs/en/usbip/ehci.rst b/docs/en/usbip/ehci.rst new file mode 100755 index 00000000..637bbe69 --- /dev/null +++ b/docs/en/usbip/ehci.rst @@ -0,0 +1,2 @@ +EHCI +================= \ No newline at end of file diff --git a/docs/en/usbip/fotg210.rst b/docs/en/usbip/fotg210.rst new file mode 100755 index 00000000..f6e566a8 --- /dev/null +++ b/docs/en/usbip/fotg210.rst @@ -0,0 +1,2 @@ +FOTG210 +=============== diff --git a/docs/en/usbip/musb.rst b/docs/en/usbip/musb.rst new file mode 100755 index 00000000..597876c0 --- /dev/null +++ b/docs/en/usbip/musb.rst @@ -0,0 +1,2 @@ +MUSB +================= \ No newline at end of file diff --git a/docs/en/usbip/ohci.rst b/docs/en/usbip/ohci.rst new file mode 100755 index 00000000..8467233b --- /dev/null +++ b/docs/en/usbip/ohci.rst @@ -0,0 +1,2 @@ +OHCI +================= \ No newline at end of file diff --git a/docs/en/usbip/xhci.rst b/docs/en/usbip/xhci.rst new file mode 100755 index 00000000..0c16c2e2 --- /dev/null +++ b/docs/en/usbip/xhci.rst @@ -0,0 +1,2 @@ +XHCI +================= \ No newline at end of file diff --git a/docs/en/version.rst b/docs/en/version.rst new file mode 100755 index 00000000..b4e6b680 --- /dev/null +++ b/docs/en/version.rst @@ -0,0 +1,180 @@ +Version Information +============================================ +If there are no special circumstances, please use the latest version. The following lists only important updates. For detailed update information, please refer to https://github.com/cherry-embedded/CherryUSB/releases. + +<= v0.10.2 Initial Version +--------------------------- + +- **Used to establish basic host/device framework, supporting only single USB IP**. +- **Host driver where each EP occupies one hardware pipe, does not support dynamic hardware pipe usage**. +- Related porting requires this version, no longer supported in subsequent versions (such as ch32, rp2040), as well as old versions of pusb2 and xhci (new versions no longer provide source code). + +v1.0.0 Transition Version +--------------------------- + +- **Host supports dynamic hardware pipe usage, no longer fixed** + +v1.1.0 Transition Version +--------------------------- + +- **Host and device support multiple USB IPs of the same type** +- **Host adds bluetooth, ch340, ftdi, cp210x, asix drivers** +- Device MSC supports multiple LUN, and CONFIG_USBDEV_MSC_BLOCK_SIZE changed to CONFIG_USBDEV_MSC_MAX_BUFSIZE + +v1.2.0 +--------------------------- + +- **Host adds rtl8152, cdc ncm drivers** +- Host adds timer to control interrupt transfers (hub modified to use timer control) +- Porting adds esp, aic host drivers +- **Optimize DWC2 code for easier reading, and add some FIFO configuration macros for users (because dwc2 fifo size is limited and there are many configuration methods, so exported to users for reasonable performance control)** +- Optimize ehci driver (qtd no longer uses dynamic allocation, bound to qh), for faster code execution + +v1.3.0 +--------------------------- + +- **Device supports automatic selection of multiple speed descriptors (enable CONFIG_USBDEV_ADVANCE_DESC)** +- Device core code unifies ep0 buffer usage for code beautification +- Host adds pl2303 driver; uses id table to support multiple VID/PID; adds user_data for user use +- Host network class driver adds TX/RX buffer macros, adds LWIP_TCPIP_CORE_LOCKING_INPUT usage for data zero-copy implementation +- Porting imports bouffalo, aic, stm32f723 device drivers +- **Fixed issue in porting host section where urb->timeout clearing had problems (no pipe alloc exception during large data transfers, mainly because transfer completed just after starting, timeout was modified to 0 before checking, didn't enter take sem flow), fixed in this version** +- EHCI enables IAAD in usbh_kill_urb, reads EHCI HCOR offset from HCCR caplength, enables OHCI for EHCI +- Adapted for NuttX OS + +v1.3.1 +--------------------------- + +- Bugfix (audio, video, CDC ECM related macros, structures, APIs) +- **Host hub enumeration thread removed, uses PSC thread, enumeration method changed to queue mode, canceled simultaneous enumeration of multiple devices functionality** +- Host scan driver information and instance uses recursive mode, removes linked list scanning +- Host network class driver optimization, supports receiving data above 16K (CDC ECM not supported), uses advanced memcpy API +- **Device protocol stack printing removed (no more printing in interrupts)** +- Porting MUSB FIFO configuration changed to obtain from FIFO table (this code references Linux), adapted for ES32, SUNXI, BEKEN + +v1.4.0 +--------------------------- + +- **Device starts supporting remote wakeup functionality, HID request(0x21), improved GET STATUS request (starting from this version can pass USB3CV testing)** +- Device adds UF2, ADB, WEBUSB functionality; MSC adds bare-metal read/write polling functionality, puts read/write in while1 execution; usbd_cdc renamed to usbd_cdc_acm +- Host adds USB WiFi(bl616), Xbox drivers; **restructured USB3.0 enumeration logic** +- **Host CDC_ACM, HID, MSC, serial transmission shared buffer, would have issues if multiple identical devices exist, changed to separate buffers** +- **Porting restructured XHCI/PUSB2 drivers, not open source**; EHCI and OHCI files renamed; added remote wakeup API +- ESP component library support +- **ChipIdea device driver support, NXP MCX series host/device support** +- ThreadX OS support + +v1.4.1 +--------------------------- + +- **Fixed device mode issue with repeated endpoint closure when using multiple altsettings, changed to close when altsetting is 0** +- **Restructured host audio descriptor parsing** +- **Added Kinetis USB IP** +- Host usbh_msc_get_maxlun request not supported by some USB drives, no error return +- Host usbh_hid_get_report_descriptor exported for user calls +- Static code checking +- GitHub action functionality + +v1.4.2 +--------------------------- + +- Device implements USB_REQUEST_GET_INTERFACE request +- **Device video transmission restructured, added dual buffering functionality** +- Device ECM restructured, maintains similar API to RNDIS +- Device and host audio volume configuration functionality restructured +- Host adds AOA driver +- C++ compatibility related modifications +- FSDEV doesn't support ISO and DWC2 high-speed hub doesn't support full-speed/low-speed checking +- **General OHCI code updates** + +v1.4.3 +--------------------------- + +- **Device EP0 processing adds thread mode** +- Device audio feedback macros and demo +- Device RNDIS adds passthrough functionality (without LWIP) +- **Host MSC moves SCSI initialization out of enumeration thread, calls it during mount phase, and adds testunit retries multiple times to be compatible with some USB drives** +- RP2040 host/device support +- **NuttX FS, serial, net component support** +- DWC2, EHCI, OHCI host DCache functionality support (improved in v1.5.0) +- T113, MCXA156, CH585, **STM32H7R support** +- Fixed issue in v1.4.1 where altsetting 0 should close all endpoints + +v1.5.0 +--------------------------- + +- **Protocol stack internal global buffer needs to use USB_ALIGN_UP alignment, for use when DCache is enabled and nocache is not enabled** +- **Improved EHCI/OHCI DCache mode handling**, add CONFIG_USB_EHCI_DESC_DCACHE_ENABLE for qh&qtd&itd, add CONFIG_USB_OHCI_DESC_DCACHE_ENABLE for ed&td +- **Platform code updates, platform-related moved to platform, added LVGL keyboard/mouse support, blackmagic support, FileX support, Zephyr disk support, ESP-IDF netif support** +- **Device SOF callback support** +- **DWC2, FSDEV ST implements low-level API and interrupts, directly calls HAL_PCD_MSP and HAL_HCD_MSP, no need for user copy-paste** +- **DWC2 implements SPLIT functionality, supports external high-speed hub interfacing with FS/LS devices in high-speed mode** +- LiteOS-M, Zephyr OS support +- Device MSC bare-metal read/write uses variable mode instead of ringbuffer +- EHCI QTD uses qtd alloc & free, saves memory, currently QH carries QTD +- RNDIS/ECM device, MSC demo updates, supports modification-free under RT-Thread +- **All memcpy replaced with usb_memcpy, ARM library has non-aligned access issues** +- **Restructured device MTP driver (commercial use)** +- **Device TMC driver (commercial use)** +- **Restructured device video transmission, directly fills UVC header in image data, achieving zero memcpy** +- **Added usb_osal_thread_schedule_other API for releasing all class threads before releasing class resources, avoiding threads still using class resources after class resources are released** +- **DWC2 device adds DCache functionality, usable for Cortex-M7/ESP32P4** +- **Bouffalo/HPM/ESP/ST/NXP DCache API support** +- CH32 device ISO updates, IP directory reclassification +- CMake, SCons, Kconfig updates +- Use USB_ASSERT_MSG for partial code checking, comprehensive warning fixes +- N32H4/MM32F5 device support +- Default enable CONFIG_USBDEV_ADVANCE_DESC + +v1.5.1 +--------------------------- + +- Support using ADB shell under RT-Thread, host serial/device CDC_ACM interfaces with RTDevice framework +- **DWC2 adds multiple USB port configuration functionality with different parameters, e.g., one full-speed and one high-speed, with different FIFO and PHY configurations** +- **EHCI control transfer memory leak when no data phase causes data QTD not to be released** +- **DWC2 reads setup using usbd_get_next_ep0_state to judge, avoiding conflict between setup and EP0 out usage under USB_OTG_DOEPINT_XFRC state** +- SIFLI USB device preliminary support + +v1.5.2 +--------------------------- + +- Some bugfixes for RT-Thread components under 1.5.1 +- IDF timer OSAL replaced with ESP timer, FreeRTOS timer may fail to start; xTaskCreate replaced with xTaskCreatePinnedToCore for multi-core convenience +- In host enumeration, removed descriptor overflow related ASSERT operations, changed to return error. String descriptor acquisition changed to only get if supported. 2ms delay changed to 10ms because some OS use 100Hz, causing delay invalidation +- **DWC2 EP mult support, split transfer code optimization, modified split-related cache handling** +- **DWC2 halt cannot clear USB_OTG_HCCHAR_EPDIR, reset port uses timeout mechanism to prevent deadlock due to disconnection during enumeration** +- Updated DWC2 AT32, STM32, Kendryte, Espressif glue code +- MUSB for standard IP structure uses independent EP control register groups, not using EPIDX register for control +- Removed all CONFIG_USBDEV_EP_NUM & CONFIG_USBHOST_PIPE_NUM, no longer used because IP itself carries this information or manufacturer SDK provides corresponding macros +- CONFIG_USBHOST_MAX_INTF_ALTSETTINGS defaults to 2 to reduce memory, only UVC and UAC use it (commercial charging), so no need to set it large +- URB interval changed from u8 to u32, maximum support 2^15 * 125us + +v1.5.3 +--------------------------- + +- Added mongoose demo +- **Device supports custom EP0 MPS, only supports commercial IPs** +- Host adds UVC bulk support, **interface number matching driver functionality**, **host address allocation changed to cyclic increment mode**, restructured lsusb command +- Host control transfer adds retry mechanism, some devices have unstable communication, retry count references Linux +- **Host RNDIS driver adds non-standard 02/02/ff interface driver matching** +- MUSB IP disables multipoint feature support +- HPMicro, ChipIdea DCache support +- IDF host MSC support +- OTG framework restructured, current port only supports HPMicro +- CI compilation functionality, supports HPMicro/Espressif/BouffaloLab + +v1.5.3.99 +--------------------------- + +Bugfix for v1.5.3 + +v1.6.0 +--------------------------- + +- **Host adds serial framework, unifies all serial-like drivers** +- **Host HID adds report descriptor parsing functionality** +- usbh_initialize adds event callback to notify users of host event changes, usually not needed, can be set to NULL +- Support gamepad device +- Added TI XMC, Infineon Edge E8x port support +- DWC2 adds usbd_dwc2_get_system_clock to replace SystemCoreClock; removes __UNALIGNED_UINT32_READ and __UNALIGNED_UINT32_WRITE macros; setup count set to 1; first setup read moved to USB_OTG_GINTSTS_ENUMDNE interrupt +- DWC2/EHCI adds root hub speed setting \ No newline at end of file diff --git a/docs/source/api/api_config.rst b/docs/source/api/api_config.rst deleted file mode 100644 index c1fe8603..00000000 --- a/docs/source/api/api_config.rst +++ /dev/null @@ -1,163 +0,0 @@ -USB CONFIG 说明 -========================= - -通用 CONFIG ---------------------- - -CONFIG_USB_PRINTF -^^^^^^^^^^^^^^^^^^^^ - -USB log 功能,默认重定向到 printf,需要注意,USB log 会在中断中使用,因此重定向的 api 不允许阻塞。举例,如果使用的是 rt-thread,请更换成 rt-kprintf - -CONFIG_USB_DBG_LEVEL -^^^^^^^^^^^^^^^^^^^^^^ - -控制 log 的打印级别 - -CONFIG_USB_PRINTF_COLOR_ENABLE -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -控制 log 颜色打印,默认开启 - -CONFIG_USB_DCACHE_ENABLE -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -不使用 nocache ram 时,开启此宏以保证数据一致性。 **使用 EHCI 时,内部依旧需要使用 nocache ram**。 - -CONFIG_USB_ALIGN_SIZE -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -USB buffer 的对齐大小,默认是 4。IP 在 dma 模式下可能对输入的 buffer有对齐要求,一般是4,如果是其他对齐方式,请修改此值。 - -USB_NOCACHE_RAM_SECTION -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -如果芯片没有 cache 功能,此宏无效。如果有,则 USB 的输入输出 buffer 必须放在 nocache ram 中,保证数据一致性。 - -设备协议栈 CONFIG ---------------------- - -CONFIG_USBDEV_REQUEST_BUFFER_LEN -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -控制传输接收和发送的 buffer 最大长度,默认是 512。 - -CONFIG_USBDEV_SETUP_LOG_PRINT -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -使能或者关闭 setup 包的 dump 信息,默认关闭。 - -CONFIG_USBDEV_DESC_CHECK -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -暂时没有实现 - -CONFIG_USBDEV_TEST_MODE -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -使能或者关闭 usb test mode - -CONFIG_USBDEV_MSC_MAX_BUFSIZE -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -msc 缓存的最大长度,缓存越大,USB 的速度越高,因为介质一般多个 block 读写速度比单个 block 高很多,比如 sd 卡。 -默认 512 ,如果是 flash 需要改成 4K, 缓存的大小需要是介质的一个 block size 的整数倍。 - -CONFIG_USBDEV_MSC_MANUFACTURER_STRING -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -CONFIG_USBDEV_MSC_PRODUCT_STRING -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -CONFIG_USBDEV_MSC_VERSION_STRING -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -CONFIG_USBDEV_MSC_POLLING -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -将 usbd_msc_sector_read 和 usbd_msc_sector_write 操作放在 while1 中运行,裸机下使用。 - -CONFIG_USBDEV_MSC_THREAD -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -使能或者关闭 msc 线程,默认关闭。usbd_msc_sector_read 和 usbd_msc_sector_write 默认是在中断中执行,所以如果开启了 os 建议开启此宏,那么, -usbd_msc_sector_read 和 usbd_msc_sector_write 就会在线程中执行。 - -CONFIG_USBDEV_MSC_PRIO -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -MSC 读写线程的优先级,默认是 4,数值越小,优先级越高 - -CONFIG_USBDEV_MSC_STACKSIZE -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -MSC 读写线程的堆栈大小,默认 2K 字节 - -CONFIG_USBDEV_RNDIS_RESP_BUFFER_SIZE -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -rndis 控制传输最大接收和发送的长度,根据 RNDIS options list 决定最小长度,默认要大于等于 156 - -CONFIG_USBDEV_RNDIS_ETH_MAX_FRAME_SIZE -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -rndis 以太网帧的最大长度,默认 1580 - -CONFIG_USBDEV_RNDIS_VENDOR_ID -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -CONFIG_USBDEV_RNDIS_VENDOR_DESC -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -CONFIG_USBDEV_RNDIS_USING_LWIP -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -rndis 与 lwip 接口的对接 - -主机协议栈 CONFIG ---------------------- - -以下参数决定了支持的最大外部hub数量,接口数,每个接口的端点数和 altsetting 数量,更改此值会影响 ram 的大小,建议根据实际情况更改。 - -.. code-block:: C - - #define CONFIG_USBHOST_MAX_RHPORTS 1 - #define CONFIG_USBHOST_MAX_EXTHUBS 1 - #define CONFIG_USBHOST_MAX_EHPORTS 4 - #define CONFIG_USBHOST_MAX_INTERFACES 6 - #define CONFIG_USBHOST_MAX_INTF_ALTSETTINGS 1 - #define CONFIG_USBHOST_MAX_ENDPOINTS 4 - -以下参数决定了支持的 class 数目,更改此值会影响 ram 的大小,建议根据实际情况更改。 - -.. code-block:: C - - #define CONFIG_USBHOST_MAX_SERIAL_CLASS 4 - #define CONFIG_USBHOST_MAX_HID_CLASS 4 - #define CONFIG_USBHOST_MAX_MSC_CLASS 2 - #define CONFIG_USBHOST_MAX_AUDIO_CLASS 1 - #define CONFIG_USBHOST_MAX_VIDEO_CLASS 1 - -CONFIG_USBHOST_PSC_PRIO -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -主机插拔线程的优先级,默认是 0,数值越小,优先级越高 - -CONFIG_USBHOST_PSC_STACKSIZE -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -主机插拔线程的堆栈大小,默认 2K 字节 - -CONFIG_USBHOST_REQUEST_BUFFER_LEN -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -控制传输能够接收或者发送的最大长度 - -CONFIG_USBHOST_CONTROL_TRANSFER_TIMEOUT -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -控制传输发送或者接收的超时时间,默认 500 ms - -CONFIG_USBHOST_MSC_TIMEOUT -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -MSC 读写传输的超时时间,默认 5s \ No newline at end of file diff --git a/docs/source/api/api_device.rst b/docs/source/api/api_device.rst deleted file mode 100644 index bc8cb100..00000000 --- a/docs/source/api/api_device.rst +++ /dev/null @@ -1,502 +0,0 @@ -设备协议栈 -========================= - -设备协议栈主要负责枚举和驱动加载,枚举这边就不说了,驱动加载,也就是接口驱动加载,主要是依靠 `usbd_add_interface` 函数,用于记录传入的接口驱动并保存到接口数组表,当主机进行类请求时就可以查找接口表进行访问了。 -在调用 `usbd_desc_register` 以后需要进行接口注册和端点注册,口诀如下: - -- 有多少个接口就调用多少次 `usbd_add_interface`,参数填相关 `xxx_init_intf`, 如果没有支持的,手动创建一个 intf 填入 -- 有多少个端点就调用多少次 `usbd_add_endpoint`,当中断完成时,会调用到注册的端点回调中。 - -参考下面这张图: - -.. figure:: img/api_device1.png - -CORE ------------------ - -端点结构体 -"""""""""""""""""""""""""""""""""""" - -端点结构体主要用于注册不同端点地址的中断完成回调函数。 - -.. code-block:: C - - struct usbd_endpoint { - uint8_t ep_addr; - usbd_endpoint_callback ep_cb; - }; - -- **ep_addr** 端点地址(带方向) -- **ep_cb** 端点完成中断回调函数。 - -.. note:: 总结一句话:in 回调函数等价于 dma 发送完成中断回调函数;out 回调函数等价于 dma 接收完成中断回调函数 - -接口结构体 -"""""""""""""""""""""""""""""""""""" - -接口结构体主要用于注册不同类设备除了标准设备请求外的其他请求,包括类设备请求、厂商设备请求和自定义设备请求。以及协议栈中的相关通知回调函数。 - -.. code-block:: C - - struct usbd_interface { - usbd_request_handler class_interface_handler; - usbd_request_handler class_endpoint_handler; - usbd_request_handler vendor_handler; - usbd_notify_handler notify_handler; - const uint8_t *hid_report_descriptor; - uint32_t hid_report_descriptor_len; - uint8_t intf_num; - }; - -- **class_interface_handler** class setup 请求回调函数,接收者为接口 -- **class_endpoint_handler** class setup 请求回调函数,接收者为端点 -- **vendor_handler** vendor setup 请求回调函数 -- **notify_handler** 中断标志、协议栈相关状态回调函数 -- **hid_report_descriptor** hid 报告描述符 -- **hid_report_descriptor_len** hid 报告描述符长度 -- **intf_num** 当前接口偏移 - -usbd_desc_register -"""""""""""""""""""""""""""""""""""" - -``usbd_desc_register`` 用来注册 USB 描述符,描述符种类包括:设备描述符、配置描述符(包含配置描述符、接口描述符、class 类描述符、端点描述符)、字符串描述符、设备限定描述符,其他速度描述符, -bos描述符,winusb 描述符。 - -.. code-block:: C - - // 开启 CONFIG_USBDEV_ADVANCE_DESC - void usbd_desc_register(uint8_t busid, const struct usb_descriptor *desc); - - // 关闭 CONFIG_USBDEV_ADVANCE_DESC - void usbd_desc_register(uint8_t busid, const uint8_t *desc); - void usbd_msosv1_desc_register(uint8_t busid, struct usb_msosv1_descriptor *desc); - void usbd_msosv2_desc_register(uint8_t busid, struct usb_msosv2_descriptor *desc); - void usbd_bos_desc_register(uint8_t busid, struct usb_bos_descriptor *desc); - void usbd_webusb_desc_register(uint8_t busid, struct usb_webusb_descriptor *desc); - -- **desc** 描述符的句柄 - -.. note:: 当前默认开启 CONFIG_USBDEV_ADVANCE_DESC,如果需要使用旧版本 API 请关闭该宏,从 v1.6.0 开始只有开启了 CONFIG_USBDEV_ADVANCE_DESC 的 API - -usbd_add_interface -"""""""""""""""""""""""""""""""""""" - -``usbd_add_interface`` 添加一个接口驱动。 **添加顺序必须按照描述符中接口顺序**。 - -.. code-block:: C - - void usbd_add_interface(uint8_t busid, struct usbd_interface *intf); - -- **busid** USB 总线 id -- **intf** 接口驱动句柄,通常从不同 class 的 `xxx_init_intf` 函数获取 - -usbd_add_endpoint -"""""""""""""""""""""""""""""""""""" - -``usbd_add_endpoint`` 添加一个端点中断完成回调函数。 - -.. code-block:: C - - void usbd_add_endpoint(uint8_t busid, struct usbd_endpoint *ep); - -- **busid** USB 总线 id -- **ep** 端点句柄 - -usbd_initialize -"""""""""""""""""""""""""""""""""""" - -``usbd_initialize`` 用来初始化 usb device 寄存器配置、usb 时钟、中断等,需要注意,此函数必须在注册描述符 API 最后。 **如果使用 os,必须放在线程中执行**。 - -.. code-block:: C - - int usbd_initialize(uint8_t busid, uintptr_t reg_base, usbd_event_handler_t event_handler); - -- **busid** USB 总线 id -- **reg_base** USB 设备寄存器基地址 -- **event_handler** 协议栈中断或者状态回调函数,event 事件 -- **return** 返回 0 表示成功,其他值表示失败 - -event 事件包括: - -.. code-block:: C - - USBD_EVENT_ERROR, /** USB error reported by the controller */ - USBD_EVENT_RESET, /** USB reset */ - USBD_EVENT_SOF, /** Start of Frame received */ - USBD_EVENT_CONNECTED, /** USB connected*/ - USBD_EVENT_DISCONNECTED, /** USB disconnected */ - USBD_EVENT_SUSPEND, /** USB connection suspended by the HOST */ - USBD_EVENT_RESUME, /** USB connection resumed by the HOST */ - - /* USB DEVICE STATUS */ - USBD_EVENT_CONFIGURED, /** USB configuration done */ - USBD_EVENT_SET_INTERFACE, /** USB interface selected */ - USBD_EVENT_SET_REMOTE_WAKEUP, /** USB set remote wakeup */ - USBD_EVENT_CLR_REMOTE_WAKEUP, /** USB clear remote wakeup */ - USBD_EVENT_INIT, /** USB init done when call usbd_initialize */ - USBD_EVENT_DEINIT, /** USB deinit done when call usbd_deinitialize */ - USBD_EVENT_UNKNOWN - -.. note:: 大部分 IP USBD_EVENT_CONNECTED 和 USBD_EVENT_DISCONNECTED 事件都不支持,当前仅 HPM 芯片支持,其余芯片自行设计vbus检测电路替代 - -usbd_deinitialize -"""""""""""""""""""""""""""""""""""" - -``usbd_deinitialize`` 用来反初始化 usb device,关闭 usb 设备时钟、中断等。 - -.. code-block:: C - - int usbd_deinitialize(uint8_t busid); - -- **busid** USB 总线 id -- **return** 返回 0 表示成功,其他值表示失败 - -CDC ACM ------------------ - -usbd_cdc_acm_init_intf -"""""""""""""""""""""""""""""""""""" - -``usbd_cdc_acm_init_intf`` 用来初始化 USB CDC ACM 类接口,并实现该接口相关的函数。 - -- ``cdc_acm_class_interface_request_handler`` 用来处理 USB CDC ACM 类 Setup 请求。 -- ``cdc_notify_handler`` 用来处理 USB CDC 其他中断回调函数。 - -.. code-block:: C - - struct usbd_interface *usbd_cdc_acm_init_intf(uint8_t busid, struct usbd_interface *intf); - -- **busid** USB 总线 id -- **return** 接口句柄 - -usbd_cdc_acm_set_line_coding -"""""""""""""""""""""""""""""""""""" - -``usbd_cdc_acm_set_line_coding`` 用来对串口进行配置,如果仅使用 USB 而不用 串口,该接口不用用户实现,使用默认。 - -.. code-block:: C - - void usbd_cdc_acm_set_line_coding(uint8_t busid, uint8_t intf, struct cdc_line_coding *line_coding); - -- **busid** USB 总线 id -- **intf** 控制接口号 -- **line_coding** 串口配置 - -usbd_cdc_acm_get_line_coding -"""""""""""""""""""""""""""""""""""" - -``usbd_cdc_acm_get_line_coding`` 用来获取串口进行配置,如果仅使用 USB 而不用 串口,该接口不用用户实现,使用默认。 - -.. code-block:: C - - void usbd_cdc_acm_get_line_coding(uint8_t busid, uint8_t intf, struct cdc_line_coding *line_coding); - -- **busid** USB 总线 id -- **intf** 控制接口号 -- **line_coding** 串口配置 - -usbd_cdc_acm_set_dtr -"""""""""""""""""""""""""""""""""""" - -``usbd_cdc_acm_set_dtr`` 用来控制串口 DTR 。如果仅使用 USB 而不用 串口,该接口不用用户实现,使用默认。 - -.. code-block:: C - - void usbd_cdc_acm_set_dtr(uint8_t busid, uint8_t intf, bool dtr); - -- **busid** USB 总线 id -- **intf** 控制接口号 -- **dtr** dtr 为1表示拉低电平,为0表示拉高电平 - -usbd_cdc_acm_set_rts -"""""""""""""""""""""""""""""""""""" - -``usbd_cdc_acm_set_rts`` 用来控制串口 RTS 。如果仅使用 USB 而不用 串口,该接口不用用户实现,使用默认。 - -.. code-block:: C - - void usbd_cdc_acm_set_rts(uint8_t busid, uint8_t intf, bool rts); - -- **busid** USB 总线 id -- **intf** 控制接口号 -- **rts** rts 为1表示拉低电平,为0表示拉高电平 - -CDC_ACM_DESCRIPTOR_INIT -"""""""""""""""""""""""""""""""""""" - -``CDC_ACM_DESCRIPTOR_INIT`` 配置了默认的 cdc acm 需要的描述符以及参数,方便用户使用。总长度为 `CDC_ACM_DESCRIPTOR_LEN` 。 - -.. code-block:: C - - CDC_ACM_DESCRIPTOR_INIT(bFirstInterface, int_ep, out_ep, in_ep, str_idx); - -- **bFirstInterface** 表示该 cdc acm 第一个接口所在所有接口的偏移 -- **int_ep** 表示中断端点地址(带方向) -- **out_ep** 表示 bulk out 端点地址(带方向) -- **in_ep** 表示 bulk in 端点地址(带方向) -- **str_idx** 控制接口对应的字符串 id - -HID ------------------ - -usbd_hid_init_intf -"""""""""""""""""""""""""""""""""""" - -``usbd_hid_init_intf`` 用来初始化 USB HID 类接口,并实现该接口相关的函数: - -- ``hid_class_interface_request_handler`` 用来处理 USB HID 类的 Setup 请求。 -- ``hid_notify_handler`` 用来处理 USB HID 其他中断回调函数。 - -.. code-block:: C - - struct usbd_interface *usbd_hid_init_intf(uint8_t busid, struct usbd_interface *intf, const uint8_t *desc, uint32_t desc_len); - -- **busid** USB 总线 id -- **desc** 报告描述符 -- **desc_len** 报告描述符长度 - -MSC ------------------ - -usbd_msc_init_intf -"""""""""""""""""""""""""""""""""""" -``usbd_msc_init_intf`` 用来初始化 MSC 类接口,并实现该接口相关函数,并且注册端点回调函数。(因为 msc bot 协议是固定的,所以不需要用于实现,因此端点回调函数自然不需要用户实现)。 - -- ``msc_storage_class_interface_request_handler`` 用于处理 USB MSC Setup 中断请求。 -- ``msc_storage_notify_handler`` 用于实现 USB MSC 其他中断回调函数。 - -- ``mass_storage_bulk_out`` 用于处理 USB MSC 端点 out 中断。 -- ``mass_storage_bulk_in`` 用于处理 USB MSC 端点 in 中断。 - -.. code-block:: C - - struct usbd_interface *usbd_msc_init_intf(uint8_t busid, struct usbd_interface *intf, const uint8_t out_ep, const uint8_t in_ep); - -- **busid** USB 总线 id -- **out_ep** out 端点地址 -- **in_ep** in 端点地址 - -usbd_msc_get_cap -"""""""""""""""""""""""""""""""""""" - -``usbd_msc_get_cap`` 用来获取存储器的 lun、扇区个数和每个扇区大小。用户必须实现该函数。 - -.. code-block:: C - - void usbd_msc_get_cap(uint8_t busid, uint8_t lun, uint32_t *block_num, uint16_t *block_size); - -- **busid** USB 总线 id -- **lun** 存储逻辑单元,暂时无用,默认支持一个 -- **block_num** 存储扇区个数 -- **block_size** 存储扇区大小 - -usbd_msc_sector_read -"""""""""""""""""""""""""""""""""""" - -``usbd_msc_sector_read`` 用来对存储器某个扇区开始的地址进行数据读取。用户必须实现该函数。 - -.. code-block:: C - - int usbd_msc_sector_read(uint8_t busid, uint8_t lun, uint32_t sector, uint8_t *buffer, uint32_t length); - -- **busid** USB 总线 id -- **lun** 存储逻辑单元,暂时无用,默认支持一个 -- **sector** 扇区偏移 -- **buffer** 存储读取的数据的指针 -- **length** 读取长度 - - -usbd_msc_sector_write -"""""""""""""""""""""""""""""""""""" - -``usbd_msc_sector_write`` 用来对存储器某个扇区开始写入数据。用户必须实现该函数。 - -.. code-block:: C - - int usbd_msc_sector_write(uint8_t busid, uint8_t lun, uint32_t sector, uint8_t *buffer, uint32_t length); - -- **busid** USB 总线 id -- **lun** 存储逻辑单元,暂时无用,默认支持一个 -- **sector** 扇区偏移 -- **buffer** 写入数据指针 -- **length** 写入长度 - -UAC ------------------ - -usbd_audio_init_intf -"""""""""""""""""""""""""""""""""""" -``usbd_audio_init_intf`` 用来初始化 USB Audio 类接口,并实现该接口相关的函数: - -- ``audio_class_interface_request_handler`` 用于处理 USB Audio Setup 接口接收者中断请求。 -- ``audio_class_endpoint_request_handler`` 用于处理 USB Audio Setup 端点接收者中断请求。 -- ``audio_notify_handler`` 用于实现 USB Audio 其他中断回调函数。 - -.. code-block:: C - - struct usbd_interface *usbd_audio_init_intf(uint8_t busid, struct usbd_interface *intf, - uint16_t uac_version, - struct audio_entity_info *table, - uint8_t num); - -- **busid** USB 总线 id -- **intf** 接口句柄 -- **uac_version** 音频类版本,UAC1.0 或 UAC2.0 -- **table** 音频实体信息表 -- **num** 音频实体信息表长度 - -usbd_audio_open -"""""""""""""""""""""""""""""""""""" - -``usbd_audio_open`` 用来开启音频数据传输。主机发送开启命令的回调函数。 - -.. code-block:: C - - void usbd_audio_open(uint8_t intf); - -- **intf** 开启的接口号 - -usbd_audio_close -"""""""""""""""""""""""""""""""""""" - -``usbd_audio_close`` 用来关闭音频数据传输。主机发送关闭命令的回调函数。 - -.. code-block:: C - - void usbd_audio_close(uint8_t intf); - -- **intf** 关闭的接口号 - -usbd_audio_set_mute -"""""""""""""""""""""""""""""""""""" - -``usbd_audio_set_mute`` 用来设置静音。 - -.. code-block:: C - - void usbd_audio_set_mute(uint8_t busid, uint8_t ep, uint8_t ch, bool mute); - -- **busid** USB 总线 id -- **ep** 要设置静音的端点 -- **ch** 要设置静音的通道 -- **mute** 为1 表示静音,0相反 - -usbd_audio_set_volume -"""""""""""""""""""""""""""""""""""" - -``usbd_audio_set_volume`` 用来设置音量。 - -.. code-block:: C - - void usbd_audio_set_volume(uint8_t busid, uint8_t ep, uint8_t ch, int volume_db); - -- **busid** USB 总线 id -- **ep** 要设置音量的端点 -- **ch** 要设置音量的通道 -- **volume_db** 要设置音量的分贝,单位 -100dB ~ 0dB - -usbd_audio_set_sampling_freq -"""""""""""""""""""""""""""""""""""" - -``usbd_audio_set_sampling_freq`` 用来设置设备上音频模块的采样率 - -.. code-block:: C - - void usbd_audio_set_sampling_freq(uint8_t busid, uint8_t ep, uint32_t sampling_freq); - -- **ep** 要设置采样率的端点 -- **sampling_freq** 要设置的采样率 - -usbd_audio_get_sampling_freq_table -"""""""""""""""""""""""""""""""""""" - -``usbd_audio_get_sampling_freq_table`` 用来获取支持的采样率列表,如果函数没有实现,则使用默认采样率列表。 UAC2 only。 - -.. code-block:: C - - void usbd_audio_get_sampling_freq_table(uint8_t busid, uint8_t ep, uint8_t **sampling_freq_table); - -- **ep** 要获取采样率的端点 -- **sampling_freq_table** 采样率列表地址,格式参考默认采样率列表 - -UVC ------------------ - -usbd_video_init_intf -"""""""""""""""""""""""""""""""""""" -``usbd_video_init_intf`` 用来初始化 USB Video 类接口,并实现该接口相关的函数: - -- ``video_class_interface_request_handler`` 用于处理 USB Video Setup 中断请求。 -- ``video_notify_handler`` 用于实现 USB Video 其他中断回调函数。 - -.. code-block:: C - - struct usbd_interface *usbd_video_init_intf(uint8_t busid, struct usbd_interface *intf, - uint32_t dwFrameInterval, - uint32_t dwMaxVideoFrameSize, - uint32_t dwMaxPayloadTransferSize); -- **busid** USB 总线 id -- **intf** 接口句柄 -- **dwFrameInterval** 视频帧间隔,单位 100ns -- **dwMaxVideoFrameSize** 最大视频帧大小 -- **dwMaxPayloadTransferSize** 最大负载传输大小 - -usbd_video_open -"""""""""""""""""""""""""""""""""""" - -``usbd_video_open`` 用来开启视频数据传输。 - -.. code-block:: C - - void usbd_video_open(uint8_t intf); - -- **intf** 开启的接口号 - -usbd_video_close -"""""""""""""""""""""""""""""""""""" - -``usbd_video_close`` 用来关闭视频数据传输。 - -.. code-block:: C - - void usbd_video_open(uint8_t intf); - -- **intf** 关闭的接口号 - -usbd_video_stream_start_write -"""""""""""""""""""""""""""""""""""" - -``usbd_video_stream_start_write`` 用来启动一帧视频数据流发送。需要搭配 `usbd_video_stream_split_transfer` 使用。 - -.. code-block:: C - - int usbd_video_stream_start_write(uint8_t busid, uint8_t ep, uint8_t *ep_buf, uint8_t *stream_buf, uint32_t stream_len, bool do_copy); - -- **busid** USB 总线 id -- **ep** 视频数据端点地址 -- **ep_buf** 视频数据端点传输缓冲区 -- **stream_buf** 一帧视频数据源缓冲区 -- **stream_len** 一帧视频数据源缓冲区大小 -- **do_copy** 是否需要将 stream_buf 数据复制到 ep_buf 中,当前仅当 stream_buf 在 nocache 区域并且未开启 DCACHE_ENABLE 时该参数才为 false - -usbd_video_stream_split_transfer -"""""""""""""""""""""""""""""""""""" - -``usbd_video_stream_split_transfer`` 用来分割视频数据流发送。需要搭配 `usbd_video_stream_start_write` 使用。 - -.. code-block:: C - - int usbd_video_stream_split_transfer(uint8_t busid, uint8_t ep); - -- **busid** USB 总线 id -- **ep** 视频数据端点地址 -- **return** 返回 true 表示一帧数据发送完成,false 表示数据未发送完成 - -RNDIS ------------------ - -CDC ECM ------------------ - -MTP ------------------ diff --git a/docs/source/api/api_host.rst b/docs/source/api/api_host.rst deleted file mode 100644 index 46d1e428..00000000 --- a/docs/source/api/api_host.rst +++ /dev/null @@ -1,317 +0,0 @@ -主机协议栈 -========================= - -关于主机协议栈中结构体的命名、分类、成员组成,参考下面这两张图: - -.. figure:: img/api_host1.png -.. figure:: img/api_host2.png - -CORE ------------------ - -CLASS 驱动信息结构体 -"""""""""""""""""""""""""""""""""""" - -.. code-block:: C - - struct usbh_class_info { - uint8_t match_flags; /* Used for product specific matches; range is inclusive */ - uint8_t bInterfaceClass; /* Base device class code */ - uint8_t bInterfaceSubClass; /* Sub-class, depends on base class. Eg. */ - uint8_t bInterfaceProtocol; /* Protocol, depends on base class. Eg. */ - const uint16_t (*id_table)[2]; /* List of Vendor/Product ID pairs */ - const struct usbh_class_driver *class_driver; - }; - -端点结构体 -"""""""""""""""""""""""""""""""""""" - -.. code-block:: C - - struct usbh_endpoint { - struct usb_endpoint_descriptor ep_desc; - }; - -接口备用结构体 -"""""""""""""""""""""""""""""""""""" - -.. code-block:: C - - struct usbh_interface_altsetting { - struct usb_interface_descriptor intf_desc; - struct usbh_endpoint ep[CONFIG_USBHOST_MAX_ENDPOINTS]; - }; - -接口结构体 -"""""""""""""""""""""""""""""""""""" - -.. code-block:: C - - struct usbh_interface { - char devname[CONFIG_USBHOST_DEV_NAMELEN]; - struct usbh_class_driver *class_driver; - void *priv; - struct usbh_interface_altsetting altsetting[CONFIG_USBHOST_MAX_INTF_ALTSETTINGS]; - uint8_t altsetting_num; - }; - -配置结构体 -"""""""""""""""""""""""""""""""""""" - -.. code-block:: C - - struct usbh_configuration { - struct usb_configuration_descriptor config_desc; - struct usbh_interface intf[CONFIG_USBHOST_MAX_INTERFACES]; - }; - -hubport 结构体 -"""""""""""""""""""""""""""""""""""" - -.. code-block:: C - - struct usbh_hubport { - bool connected; /* True: device connected; false: disconnected */ - uint8_t port; /* Hub port index */ - uint8_t dev_addr; /* device address */ - uint8_t speed; /* device speed */ - uint8_t depth; /* distance from root hub */ - uint8_t route; /* route string */ - uint8_t slot_id; /* slot id */ - struct usb_device_descriptor device_desc; - struct usbh_configuration config; - const char *iManufacturer; - const char *iProduct; - const char *iSerialNumber; - uint8_t *raw_config_desc; - struct usb_setup_packet *setup; - struct usbh_hub *parent; - struct usbh_hub *self; /* if this hubport is a hub */ - struct usbh_bus *bus; - struct usb_endpoint_descriptor ep0; - struct usbh_urb ep0_urb; - usb_osal_mutex_t mutex; - }; - -hub 结构体 -"""""""""""""""""""""""""""""""""""" - -.. code-block:: C - - struct usbh_hub { - bool connected; - bool is_roothub; - uint8_t index; - uint8_t hub_addr; - uint8_t speed; - uint8_t nports; - uint8_t powerdelay; - uint8_t tt_think; - bool ismtt; - struct usb_hub_descriptor hub_desc; /* USB 2.0 only */ - struct usb_hub_ss_descriptor hub_ss_desc; /* USB 3.0 only */ - struct usbh_hubport child[CONFIG_USBHOST_MAX_EHPORTS]; - struct usbh_hubport *parent; - struct usbh_bus *bus; - struct usb_endpoint_descriptor *intin; - struct usbh_urb intin_urb; - uint8_t *int_buffer; - struct usb_osal_timer *int_timer; - }; - -usbh_initialize -"""""""""""""""""""""""""""""""""""" - -``usbh_initialize`` 用来初始化 usb 主机协议栈,包括:初始化 usb 主机控制器,创建 roothub 设备,创建 hub 检测线程。 - -.. code-block:: C - - int usbh_initialize(uint8_t busid, uint32_t reg_base, usbh_event_handler_t event_handler); - -- **busid** bus id,从 0开始,不能超过 `CONFIG_USBHOST_MAX_BUS` -- **reg_base** hcd 寄存器基地址 -- **event_handler** host 事件回调函数,可以为NULL -- **return** 0 表示正常其他表示错误 - -usbh_find_class_instance -"""""""""""""""""""""""""""""""""""" - -``usbh_find_class_instance`` 根据注册的 class 名称查找对应的 class 结构体句柄。 - -.. code-block:: C - - void *usbh_find_class_instance(const char *devname); - -- **devname** class 名称 -- **return** class 结构体句柄 - -lsusb -"""""""""""""""""""""""""""""""""""" - -``lsusb`` 用来查看和操作 hub 上的设备信息。需要借助 shell 插件使用。 - -.. code-block:: C - - int lsusb(int argc, char **argv); - -SERIAL ------------------ - -usbh_serial_open -"""""""""""""""""""""""""""""""""""" - -``usbh_serial_open`` 根据路径打开一个串口设备。 - -.. code-block:: C - - struct usbh_serial *usbh_serial_open(const char *devname, uint32_t open_flags); - -- **devname** 串口路径 -- **open_flags** 打开标志,参考 `USBH_SERIAL_OFLAG_*` 定义 -- **return** serial 结构体句柄 - -usbh_serial_close -"""""""""""""""""""""""""""""""""""" - -``usbh_serial_close`` 关闭串口设备。 - -.. code-block:: C - - void usbh_serial_close(struct usbh_serial *serial); - -- **serial** serial 结构体句柄 - -usbh_serial_control -"""""""""""""""""""""""""""""""""""" - -``usbh_serial_control`` 对串口进行配置。 - -.. code-block:: C - - int usbh_serial_control(struct usbh_serial *serial, int cmd, void *arg); - -- **serial** serial 结构体句柄 -- **cmd** 控制命令,参考 `USBH_SERIAL_CMD_*` 定义 -- **arg** 控制参数指针 -- **return** 0 表示正常其他表示错误 - -usbh_serial_write -"""""""""""""""""""""""""""""""""""" - -``usbh_serial_write`` 向串口写数据。 - -.. code-block:: C - - int usbh_serial_write(struct usbh_serial *serial, const void *buffer, uint32_t buflen); - -- **serial** serial 结构体句柄 -- **buffer** 数据缓冲区指针 -- **buflen** 要写入的数据长度 -- **return** 实际写入的数据长度或者错误码 - -.. note:: 如果没有开启 CONFIG_USB_DCACHE_ENABLE,则 buffer 需要是 nocache区域,否则需要是对齐到 CONFIG_USB_ALIGN_SIZE 的区域。 - -usbh_serial_read -"""""""""""""""""""""""""""""""""""" - -``usbh_serial_read`` 从串口读数据。 **如果没有设置波特率,不允许使用该 API,设置波特率后,内部会开启 rx 接收并将数据写入 ringbuf **。 - -.. code-block:: C - - int usbh_serial_read(struct usbh_serial *serial, void *buffer, uint32_t buflen); - -- **serial** serial 结构体句柄 -- **buffer** 数据缓冲区指针 -- **buflen** 要读取的最大数据长度 -- **return** 实际读取的数据长度或者错误码 - -.. note:: 由于内部使用了 ringbuffer,对于用户的 buffer 属性没有限制。 - -usbh_serial_cdc_write_async -"""""""""""""""""""""""""""""""""""" - -``usbh_serial_cdc_write_async`` 异步从串口读数据。 **如果设置了波特率,不允许使用该 API**。 - -.. code-block:: C - - int usbh_serial_cdc_write_async(struct usbh_serial *serial, uint8_t *buffer, uint32_t buflen, usbh_complete_callback_t complete, void *arg); - -- **serial** serial 结构体句柄 -- **buffer** 数据缓冲区指针 -- **buflen** 要发送的数据长度 -- **complete** 读数据完成回调函数 -- **arg** 回调函数参数 -- **return** 0 表示正常其他表示错误 - -.. note:: 如果没有开启 CONFIG_USB_DCACHE_ENABLE,则 buffer 需要是 nocache区域,否则需要是对齐到 CONFIG_USB_ALIGN_SIZE 的区域。 - -usbh_serial_cdc_read_async -"""""""""""""""""""""""""""""""""""" - -``usbh_serial_cdc_read_async`` 异步从串口读数据。 **如果设置了波特率,不允许使用该 API,设置波特率后,内部会开启 rx 接收并将数据写入 ringbuf **。 - -.. code-block:: C - - int usbh_serial_cdc_read_async(struct usbh_serial *serial, uint8_t *buffer, uint32_t buflen, usbh_complete_callback_t complete, void *arg); - -- **serial** serial 结构体句柄 -- **buffer** 数据缓冲区指针 -- **buflen** 要读取的最大数据长度,一次最高 16K。并且需要是 wMaxPacketSize 的整数倍 -- **complete** 读数据完成回调函数 -- **arg** 回调函数参数 -- **return** 0 表示正常其他表示错误 - -.. note:: 如果没有开启 CONFIG_USB_DCACHE_ENABLE,则 buffer 需要是 nocache区域,否则需要是对齐到 CONFIG_USB_ALIGN_SIZE 的区域。 - -HID ------------------ - -MSC ------------------ - -usbh_msc_scsi_init -"""""""""""""""""""""""""""""""""""" - -``usbh_msc_scsi_init`` 初始化 msc scsi 设备。获取 MSC 状态和容量信息。 - -.. code-block:: C - - int usbh_msc_scsi_init(struct usbh_msc *msc_class); - -- **msc_class** msc 结构体句柄 -- **return** 0 表示正常其他表示错误 - -usbh_msc_scsi_write10 -"""""""""""""""""""""""""""""""""""" - -``usbh_msc_scsi_write10`` 向 msc 设备写数据。 - -.. code-block:: C - - int usbh_msc_scsi_write10(struct usbh_msc *msc_class, uint32_t start_sector, const uint8_t *buffer, uint32_t nsectors); - -- **msc_class** msc 结构体句柄 -- **start_sector** 起始扇区 -- **buffer** 数据缓冲区指针 -- **nsectors** 要写入的扇区数 -- **return** 返回 0 表示正常其他表示错误 - -usbh_msc_scsi_read10 -"""""""""""""""""""""""""""""""""""" - -``usbh_msc_scsi_read10`` 从 msc 设备读数据。 - -.. code-block:: C - - int usbh_msc_scsi_read10(struct usbh_msc *msc_class, uint32_t start_sector, uint8_t *buffer, uint32_t nsectors); - -- **msc_class** msc 结构体句柄 -- **start_sector** 起始扇区 -- **buffer** 数据缓冲区指针 -- **nsectors** 要读取的扇区数 -- **return** 返回 0 表示正常其他表示错误 - -NETWORK ------------------ - -已对接 lwIP 协议栈或者其他网络协议栈,使用 socket API 即可。 \ No newline at end of file diff --git a/docs/source/api/api_port.rst b/docs/source/api/api_port.rst deleted file mode 100644 index c214daa7..00000000 --- a/docs/source/api/api_port.rst +++ /dev/null @@ -1,266 +0,0 @@ -主从驱动 -========================= - -.. note:: 请注意,v1.1 版本开始增加 busid 形参,其余保持不变,所以 API 说明不做更新 - -device controller(dcd) -------------------------- - -usb_dc_init -"""""""""""""""""""""""""""""""""""" - -``usb_dc_init`` 用于初始化 usb device controller 寄存器,设置 usb 引脚、时钟、中断等等。 **此函数不对用户开放**。 - -.. code-block:: C - - int usb_dc_init(void); - -- **return** 返回 0 表示正确,其他表示错误 - -usb_dc_deinit -"""""""""""""""""""""""""""""""""""" - -``usb_dc_deinit`` 用于反初始化 usb device controller 寄存器。 **此函数不对用户开放**。 - -.. code-block:: C - - int usb_dc_deinit(void); - -- **return** 返回 0 表示正确,其他表示错误 - -usbd_set_address -"""""""""""""""""""""""""""""""""""" - -``usbd_set_address`` 设置设备地址。 **此函数不对用户开放**。 - -.. code-block:: C - - int usbd_set_address(const uint8_t addr); - -- **addr** 设备地址 -- **return** 返回 0 表示正确,其他表示错误 - -usbd_ep_open -"""""""""""""""""""""""""""""""""""" - -``usbd_ep_open`` 设置端点的属性,开启对应端点的中断。 **此函数不对用户开放**。 - -.. code-block:: C - - int usbd_ep_open(const struct usb_endpoint_descriptor *ep); - -- **ep** 端点描述符 -- **return** 返回 0 表示正确,其他表示错误 - -usbd_ep_close -"""""""""""""""""""""""""""""""""""" - -``usbd_ep_close`` 关闭端点。 **此函数不对用户开放**。 - -.. code-block:: C - - int usbd_ep_close(const uint8_t ep); - -- **ep** 端点地址 -- **return** 返回 0 表示正确,其他表示错误 - -usbd_ep_set_stall -"""""""""""""""""""""""""""""""""""" - -``usbd_ep_set_stall`` 将端点设置成 stall 状态并发送 stall 握手包。 **此函数对用户开放**。 - -.. code-block:: C - - int usbd_ep_set_stall(const uint8_t ep); - -- **ep** 端点地址 -- **return** 返回 0 表示正确,其他表示错误 - -usbd_ep_clear_stall -"""""""""""""""""""""""""""""""""""" - -``usbd_ep_clear_stall`` 清除端点的 stall 状态。 **此函数不对用户开放**。 - -.. code-block:: C - - int usbd_ep_clear_stall(const uint8_t ep); - -- **ep** 端点地址 -- **return** 返回 0 表示正确,其他表示错误 - -usbd_ep_is_stalled -"""""""""""""""""""""""""""""""""""" - -``usbd_ep_is_stalled`` 读取当前端点的 stall 状态。 **此函数不对用户开放**。 - -.. code-block:: C - - int usbd_ep_is_stalled(const uint8_t ep, uint8_t *stalled); - -- **ep** 端点地址 -- **return** 返回 1 表示 stalled,0 表示没有 stall - -usbd_ep_start_write -"""""""""""""""""""""""""""""""""""" - -``usbd_ep_start_write`` 启动端点发送,发送完成以后,会调用注册的 in 端点传输完成中断回调函数。该函数为异步发送。 **此函数对用户开放**。 - -.. code-block:: C - - int usbd_ep_start_write(const uint8_t ep, const uint8_t *data, uint32_t data_len); - -- **ep** in 端点地址 -- **data** 发送数据缓冲区 -- **data_len** 发送长度,原则上无限长,推荐 16K 字节以内 -- **return** 返回 0 表示正确,其他表示错误 - -usbd_ep_start_read -"""""""""""""""""""""""""""""""""""" - -``usbd_ep_start_read`` 启动端点接收,接收完成以后,会调用注册的 out 端点传输完成中断回调函数。该函数为异步接收。 **此函数对用户开放**。 - -.. code-block:: C - - int usbd_ep_start_read(const uint8_t ep, uint8_t *data, uint32_t data_len); - -- **ep** out 端点地址 -- **data** 接收数据缓冲区 -- **data_len** 接收长度,原则上无限长,推荐 16K 字节以内,并且推荐是最大包长的整数倍 -- **return** 返回 0 表示正确,其他表示错误 - -.. note:: 启动接收以后,以下两种情况,会进入传输完成中断:1、最后一包为短包(小于 EP MPS);2、接收总长度等于 data_len - -.. note:: 对于 bulk 传输,data_len 通常设计为 EP MPS,以下三种情况可以修改为多个 EP MPS: 固定长度;自定义协议并携带长度(MSC); 主机手动发送 ZLP 或者短包(RNDIS) - -host controller(hcd) ------------------------- - -usb_hc_init -"""""""""""""""""""""""""""""""""""" - -``usb_hc_init`` 用于初始化 usb host controller 寄存器,设置 usb 引脚、时钟、中断等等。 **此函数不对用户开放**。 - -.. code-block:: C - - int usb_hc_init(void); - -- **return** 返回 0 表示正确,其他表示错误 - -usb_hc_deinit -"""""""""""""""""""""""""""""""""""" - -``usb_hc_deinit`` 用于反初始化 usb host controller 寄存器。 **此函数不对用户开放**。 - -.. code-block:: C - - int usb_hc_deinit(void); - -- **return** 返回 0 表示正确,其他表示错误 - -usbh_roothub_control -"""""""""""""""""""""""""""""""""""" - -``usbh_roothub_control`` 用来对 roothub 发起请求, **此函数不对用户开放**。 - -.. code-block:: C - - int usbh_roothub_control(struct usb_setup_packet *setup, uint8_t *buf); - -- **setup** 请求 -- **buf** 接收缓冲区 -- **return** 返回 0 表示正确,其他表示错误 - -usbh_submit_urb -"""""""""""""""""""""""""""""""""""" - -``usbh_submit_urb`` 对某个地址上的端点进行数据请求。 **此函数对用户开放**。 - -.. code-block:: C - - int usbh_submit_urb(struct usbh_urb *urb); - -- **urb** usb 请求块 -- **return** 返回 0 表示正确,其他表示错误 - -其中, `urb` 结构体信息如下: - -.. code-block:: C - - struct usbh_urb { - usb_slist_t list; - void *hcpriv; - struct usbh_hubport *hport; - struct usb_endpoint_descriptor *ep; - uint8_t data_toggle; - uint8_t interval; - struct usb_setup_packet *setup; - uint8_t *transfer_buffer; - uint32_t transfer_buffer_length; - int transfer_flags; - uint32_t actual_length; - uint32_t timeout; - int errorcode; - uint32_t num_of_iso_packets; - uint32_t start_frame; - usbh_complete_callback_t complete; - void *arg; - #if defined(__ICCARM__) || defined(__ICCRISCV__) || defined(__ICCRX__) - struct usbh_iso_frame_packet *iso_packet; - #else - struct usbh_iso_frame_packet iso_packet[0]; - #endif - }; - -- **hcpriv** 主机控制器驱动私有成员 -- **hport** 当前 urb 使用的 hport -- **ep** 当前 urb 使用的 ep -- **data_toggle** 当前 data toggle -- **interval** urb 传输间隔,单位 us,如果 interval 大于 1000us,则需要使用软件定时器来维护 -- **setup** setup 请求缓冲区,端点0使用 -- **transfer_buffer** 传输的数据缓冲区 -- **transfer_buffer_length** 传输长度 -- **transfer_flags** 传输时携带的 flag -- **actual_length** 实际传输长度 -- **timeout** 传输超时时间,为 0 该函数则为非阻塞,可在中断中使用 -- **errorcode** 错误码 -- **num_of_iso_packets** iso 帧或者微帧个数 -- **complete** 传输完成回调函数 -- **arg** 传输完成时携带的参数 -- **iso_packet** iso 数据包 - -.. note:: timeout 如何没有特别对时间的要求,必须设置成 0xffffffff,原则上不允许超时,如果超时了,一般不能再继续工作 - -`errorcode` 可以返回以下值: - -.. code-block:: C - - #define USB_ERR_NOMEM 1 - #define USB_ERR_INVAL 2 - #define USB_ERR_NODEV 3 - #define USB_ERR_NOTCONN 4 - #define USB_ERR_NOTSUPP 5 - #define USB_ERR_BUSY 6 - #define USB_ERR_RANGE 7 - #define USB_ERR_STALL 8 - #define USB_ERR_BABBLE 9 - #define USB_ERR_NAK 10 - #define USB_ERR_DT 11 - #define USB_ERR_IO 12 - #define USB_ERR_SHUTDOWN 13 - #define USB_ERR_TIMEOUT 14 - -其中 `iso_packet` 结构体信息如下: - -.. code-block:: C - - struct usbh_iso_frame_packet { - uint8_t *transfer_buffer; - uint32_t transfer_buffer_length; - uint32_t actual_length; - int errorcode; - }; - -- **transfer_buffer** 传输的数据缓冲区 -- **transfer_buffer_length** 传输长度 -- **actual_length** 实际传输长度 -- **errorcode** 错误码 \ No newline at end of file diff --git a/docs/source/api/img/api_device1.png b/docs/source/api/img/api_device1.png deleted file mode 100644 index ba218b65..00000000 Binary files a/docs/source/api/img/api_device1.png and /dev/null differ diff --git a/docs/source/api/img/api_host1.png b/docs/source/api/img/api_host1.png deleted file mode 100644 index 82932f50..00000000 Binary files a/docs/source/api/img/api_host1.png and /dev/null differ diff --git a/docs/source/api/img/api_host2.png b/docs/source/api/img/api_host2.png deleted file mode 100644 index 7f6d60b8..00000000 Binary files a/docs/source/api/img/api_host2.png and /dev/null differ diff --git a/docs/source/class/class_audio.rst b/docs/source/class/class_audio.rst deleted file mode 100644 index d1a9e207..00000000 --- a/docs/source/class/class_audio.rst +++ /dev/null @@ -1,4 +0,0 @@ -UAC -========================= - -参考官方 audio 相关 pdf \ No newline at end of file diff --git a/docs/source/class/class_cdc.rst b/docs/source/class/class_cdc.rst deleted file mode 100644 index d3ed560f..00000000 --- a/docs/source/class/class_cdc.rst +++ /dev/null @@ -1,4 +0,0 @@ -CDC -========================= - -参考官方 cdc 相关 pdf \ No newline at end of file diff --git a/docs/source/class/class_hid.rst b/docs/source/class/class_hid.rst deleted file mode 100644 index 0f9ef13d..00000000 --- a/docs/source/class/class_hid.rst +++ /dev/null @@ -1,4 +0,0 @@ -HID -========================= - -参考官方 hid 相关 pdf \ No newline at end of file diff --git a/docs/source/class/class_msc.rst b/docs/source/class/class_msc.rst deleted file mode 100644 index c01a359c..00000000 --- a/docs/source/class/class_msc.rst +++ /dev/null @@ -1,4 +0,0 @@ -MSC -========================= - -参考官方 msc 相关 pdf \ No newline at end of file diff --git a/docs/source/class/class_video.rst b/docs/source/class/class_video.rst deleted file mode 100644 index cabe5173..00000000 --- a/docs/source/class/class_video.rst +++ /dev/null @@ -1,4 +0,0 @@ -UVC -========================= - -参考官方 video 相关 pdf \ No newline at end of file diff --git a/docs/source/class/winusb.rst b/docs/source/class/winusb.rst deleted file mode 100644 index 8c74d3b7..00000000 --- a/docs/source/class/winusb.rst +++ /dev/null @@ -1,2 +0,0 @@ -WINUSB -========================= diff --git a/docs/source/conf.py b/docs/source/conf.py deleted file mode 100644 index 6174f623..00000000 --- a/docs/source/conf.py +++ /dev/null @@ -1,37 +0,0 @@ -# Configuration file for the Sphinx documentation builder. - -# -- Project information - -project = 'CherryUSB' -copyright = '2022 ~ 2025, sakumisu' -author = 'sakumisu' - -release = '1.6.0' -version = '1.6.0' - -# -- General configuration - -extensions = [ - 'sphinx.ext.duration', - 'sphinx.ext.doctest', - 'sphinx.ext.autodoc', - 'sphinx.ext.autosummary', - 'sphinx.ext.intersphinx', - 'recommonmark', - 'sphinx_markdown_tables' -] - -intersphinx_mapping = { -# 'python': ('https://docs.python.org/3/', None), -# 'sphinx': ('https://www.sphinx-doc.org/en/master/', None), -} -intersphinx_disabled_domains = ['std'] - -templates_path = ['_templates'] - -# -- Options for HTML output - -html_theme = 'sphinx_rtd_theme' - -# -- Options for EPUB output -epub_show_urls = 'footnote' diff --git a/docs/source/demo/img/cherryadb.png b/docs/source/demo/img/cherryadb.png deleted file mode 100644 index 512586b9..00000000 Binary files a/docs/source/demo/img/cherryadb.png and /dev/null differ diff --git a/docs/source/demo/img/otg.png b/docs/source/demo/img/otg.png deleted file mode 100644 index 9605176a..00000000 Binary files a/docs/source/demo/img/otg.png and /dev/null differ diff --git a/docs/source/demo/img/rtt_adb_shell1.png b/docs/source/demo/img/rtt_adb_shell1.png deleted file mode 100644 index df4964a2..00000000 Binary files a/docs/source/demo/img/rtt_adb_shell1.png and /dev/null differ diff --git a/docs/source/demo/img/rtt_adb_shell2.png b/docs/source/demo/img/rtt_adb_shell2.png deleted file mode 100644 index 88d99a6a..00000000 Binary files a/docs/source/demo/img/rtt_adb_shell2.png and /dev/null differ diff --git a/docs/source/demo/img/usbh_serial.png b/docs/source/demo/img/usbh_serial.png deleted file mode 100644 index da929c4a..00000000 Binary files a/docs/source/demo/img/usbh_serial.png and /dev/null differ diff --git a/docs/source/demo/usb_otg.rst b/docs/source/demo/usb_otg.rst deleted file mode 100644 index 78692cc0..00000000 --- a/docs/source/demo/usb_otg.rst +++ /dev/null @@ -1,15 +0,0 @@ -OTG 功能的使用 -========================= - -如果需要使用 OTG 功能,首先使用的芯片需要支持 ID 检测功能,然后使能 ``CONFIG_USB_OTG_ENABLE`` 宏,将之前的例程中 ``usbh_initialize`` 或者 ``usbh_initialize`` -替换成 ``usbotg_initialize`` 即可。 - -ID 检测电路根据不同的 USB 接口类型有所不同,常见的有 micro-USB 和 USB-C 两种接口类型。 - -- 如果是 micro-USB 接口,则将 ID 线连接到芯片的 ID 引脚,并使能 ID 功能即可。 -- 如果是 USB-C 接口,由于没有 ID 引脚,则需要借助 CC 电路转换成 ID 然后连接到芯片的 ID 引脚,常见电路图如下所示(DNP 表示不焊接): - -.. figure:: img/otg.png - - -.. note:: 除 ID 引脚以外,还需要增加 VBUS 输出开关控制,当工作在 host 时,开启 VBUS 供电,当工作在 device 时,关闭 VBUS 供电。 \ No newline at end of file diff --git a/docs/source/demo/usbd_adb.rst b/docs/source/demo/usbd_adb.rst deleted file mode 100644 index 92a3043e..00000000 --- a/docs/source/demo/usbd_adb.rst +++ /dev/null @@ -1,28 +0,0 @@ -usbd_adb -=============== - -本节主要介绍如何使用 adb device。支持 **cherrysh** 和 rt-thread **msh**,只需要在 main 中添加以下初始化即可。 - -.. code-block:: C - - cherryadb_init(0, xxxxx); - -如果使用 rt-thread,还需要在 menuconfig 中使能 adb device。 - -.. figure:: img/rtt_adb_shell1.png - -进入 adb --------------- - -- 使用 **cherrysh** 时枚举完成以后自动进入 adb 模式 -- 使用 **msh** 需要在 **msh** 中输入 ``adb_enter`` 进入 adb 模式 - -退出 adb --------------- - -- 使用 **cherrysh** 时输入 ``exit`` 退出 adb 模式 -- 使用 **msh** 需要在 **msh** 中输入 ``adb_exit`` 退出 adb 模式 - -.. figure:: img/cherryadb.png - -.. figure:: img/rtt_adb_shell2.png diff --git a/docs/source/demo/usbd_audiov1.rst b/docs/source/demo/usbd_audiov1.rst deleted file mode 100644 index 794ac8f6..00000000 --- a/docs/source/demo/usbd_audiov1.rst +++ /dev/null @@ -1,7 +0,0 @@ -usbd_audiov1 -=============== - -在使用 UAC1.0 时,需要注意以下几点: - -- 在使用windows 时,当修改描述符任意参数时,必须同步修改字符串描述符,并且卸载驱动,否则windows会认为设备未更改,继续使用旧的驱动,导致无法识别设备。Linux 不受此限制。 -- QQ 群文件中下载 RemoveGhostDev64.exe 可以自动删除所有 USB 注册的驱动信息,无需第一步 \ No newline at end of file diff --git a/docs/source/demo/usbd_audiov2.rst b/docs/source/demo/usbd_audiov2.rst deleted file mode 100644 index 0390f17d..00000000 --- a/docs/source/demo/usbd_audiov2.rst +++ /dev/null @@ -1,9 +0,0 @@ -usbd_audiov2 -=============== - -在使用 UAC2.0 时,需要注意以下几点: - -- 在使用windows 时,当修改描述符任意参数时,必须同步修改字符串描述符,并且卸载驱动,否则windows会认为设备未更改,继续使用旧的驱动,导致无法识别设备。Linux 不受此限制。 -- QQ 群文件中下载 RemoveGhostDev64.exe 可以自动删除所有 USB 注册的驱动信息,无需第一步 -- windows 10 uac2.0 功能不完善,请使用 windows 11 测试uac2.0 功能。Linux 不受此限制 -- windows 中设置的采样率表范围在多通道时(通道数大于2)计算有误,比如设置 8K~96K,那么实际是大于等于8K 小于96K,而非小于等于96K。Linux 不受此限制 diff --git a/docs/source/demo/usbd_cdc_acm.rst b/docs/source/demo/usbd_cdc_acm.rst deleted file mode 100644 index be330b4c..00000000 --- a/docs/source/demo/usbd_cdc_acm.rst +++ /dev/null @@ -1,104 +0,0 @@ -usbd_cdc_acm -=============== - -本 demo 主要用于演示 cdc acm 功能,包含收发测试,DTR 控制,ZLP 测试,性能测试。 - -- 开辟读写 buffer,用于收发数据,并且buffer需要用 nocache 修饰,这里我们读写都是用 2048字节,是为了后面的 ZLP 测试和性能测试使用。 - -.. code-block:: C - - USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t read_buffer[2048]; /* 2048 is only for test speed , please use CDC_MAX_MPS for common*/ - USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t write_buffer[2048]; - - -- 在协议栈事件回调中,我们需要在枚举完成后启动第一次传输,并清除相关 flag,可以在 reset 事件中清除,也可以在 configured 事件中清除。 - -.. code-block:: C - - static void usbd_event_handler(uint8_t busid, uint8_t event) - { - switch (event) { - case USBD_EVENT_RESET: - break; - case USBD_EVENT_CONNECTED: - break; - case USBD_EVENT_DISCONNECTED: - break; - case USBD_EVENT_RESUME: - break; - case USBD_EVENT_SUSPEND: - break; - case USBD_EVENT_CONFIGURED: - ep_tx_busy_flag = false; - /* setup first out ep read transfer */ - usbd_ep_start_read(busid, CDC_OUT_EP, read_buffer, 2048); - break; - case USBD_EVENT_SET_REMOTE_WAKEUP: - break; - case USBD_EVENT_CLR_REMOTE_WAKEUP: - break; - - default: - break; - } - } - -- 在接收完成中断中继续发起接收;在发送完成中断中判断是否需要发送 ZLP。 - -.. code-block:: C - - void usbd_cdc_acm_bulk_out(uint8_t busid, uint8_t ep, uint32_t nbytes) - { - USB_LOG_RAW("actual out len:%d\r\n", nbytes); - // for (int i = 0; i < 100; i++) { - // printf("%02x ", read_buffer[i]); - // } - // printf("\r\n"); - /* setup next out ep read transfer */ - usbd_ep_start_read(busid, CDC_OUT_EP, read_buffer, 2048); - } - - void usbd_cdc_acm_bulk_in(uint8_t busid, uint8_t ep, uint32_t nbytes) - { - USB_LOG_RAW("actual in len:%d\r\n", nbytes); - - if ((nbytes % usbd_get_ep_mps(busid, ep)) == 0 && nbytes) { - /* send zlp */ - usbd_ep_start_write(busid, CDC_IN_EP, NULL, 0); - } else { - ep_tx_busy_flag = false; - } - } - -- 以下是为了测试 DTR 功能并控制 USB 发送,DTR 和 RTS 只用于搭配 UART 使用,如果是纯 USB,没什么用,这里仅做测试。DTR 开关使用任意串口上位机并勾选 DTR。 - -.. code-block:: C - - void usbd_cdc_acm_set_dtr(uint8_t busid, uint8_t intf, bool dtr) - { - if (dtr) { - dtr_enable = 1; - } else { - dtr_enable = 0; - } - } - -- 在主函数中一直调用发送即可 - -.. code-block:: C - - void cdc_acm_data_send_with_dtr_test(uint8_t busid) - { - if (dtr_enable) { - ep_tx_busy_flag = true; - usbd_ep_start_write(busid, CDC_IN_EP, write_buffer, 2048); - while (ep_tx_busy_flag) { - } - } - } - -- 上述我们需要注意,长度设置为 2048 是为了测试 ZLP 功能,通常实际使用时,接收长度应该使用 CDC_MAX_MPS 。具体原因参考 :ref:`usb_ext` -- 如果需要做性能测试,使用 tools/test_srcipts/test_cdc_speed.py 进行测试,并在测试之前删除 `usbd_cdc_acm_bulk_out` 和 `usbd_cdc_acm_bulk_in` 中的打印,否则会影响测试结果。 - - -此外,对于 CDC ACM 搭配 OS 的情况,通常我们 read 使用异步并将数据存储到 ringbuffer 中,write 使用同步搭配 sem 使用。 \ No newline at end of file diff --git a/docs/source/demo/usbd_ecm.rst b/docs/source/demo/usbd_ecm.rst deleted file mode 100644 index c4c64ab5..00000000 --- a/docs/source/demo/usbd_ecm.rst +++ /dev/null @@ -1,2 +0,0 @@ -usbd_cdc_ecm -=============== diff --git a/docs/source/demo/usbd_hid.rst b/docs/source/demo/usbd_hid.rst deleted file mode 100644 index 68b6b285..00000000 --- a/docs/source/demo/usbd_hid.rst +++ /dev/null @@ -1,4 +0,0 @@ -usbd_hid -=============== - -HID 功能比较简单,因此不作赘述,需要注意,使用 hid custom 例程时,需要搭配 `tools/test_srcipts/test_hid_inout.py` 使用。 \ No newline at end of file diff --git a/docs/source/demo/usbd_msc.rst b/docs/source/demo/usbd_msc.rst deleted file mode 100644 index ff59aada..00000000 --- a/docs/source/demo/usbd_msc.rst +++ /dev/null @@ -1,39 +0,0 @@ -usbd_msc -=============== - -本节主要演示 USB 模拟 U 盘功能。默认使用RAM 作为存储介质模拟 U 盘。 - -- 实现 U 盘的读写和获取容量接口,注意,容量 block_num 为虚拟的,实际没有这么多 block,读写的数据超过 BLOCK_COUNT 会丢弃。 - -block_size 一般为 512/2048/4096。 - -.. code-block:: C - - void usbd_msc_get_cap(uint8_t busid, uint8_t lun, uint32_t *block_num, uint32_t *block_size) - { - *block_num = 1000; //Pretend having so many buffer,not has actually. - *block_size = BLOCK_SIZE; - } - int usbd_msc_sector_read(uint8_t busid, uint8_t lun, uint32_t sector, uint8_t *buffer, uint32_t length) - { - if (sector < BLOCK_COUNT) - memcpy(buffer, mass_block[sector].BlockSpace, length); - return 0; - } - - int usbd_msc_sector_write(uint8_t busid, uint8_t lun, uint32_t sector, uint8_t *buffer, uint32_t length) - { - if (sector < BLOCK_COUNT) - memcpy(mass_block[sector].BlockSpace, buffer, length); - return 0; - } - -- 默认上述 API 在中断中执行,如果需要在非中断中执行,可以选择如下: - -1,裸机下开启 `CONFIG_USBDEV_MSC_POLLING` 并在 while1 中调用 `usbd_msc_polling`,则读写函数在 while1 中执行。 - -2, OS 下开启 `CONFIG_USBDEV_MSC_THREAD`,则读写函数在线程中执行。 - -- 修改 `CONFIG_USBDEV_MSC_BUFSIZE` 会影响 U 盘的读写速度,必须是 block_size 的整数倍,当然,也会增加 RAM 的占用。 - -- 如果 RAM 例程可以用,但是介质更换成 SD 或者 FLASH 后不可用,则一定是介质驱动问题。 \ No newline at end of file diff --git a/docs/source/demo/usbd_rndis.rst b/docs/source/demo/usbd_rndis.rst deleted file mode 100644 index 40fba402..00000000 --- a/docs/source/demo/usbd_rndis.rst +++ /dev/null @@ -1,2 +0,0 @@ -usbd_rndis -=============== diff --git a/docs/source/demo/usbd_vendor.rst b/docs/source/demo/usbd_vendor.rst deleted file mode 100644 index b38631b1..00000000 --- a/docs/source/demo/usbd_vendor.rst +++ /dev/null @@ -1,44 +0,0 @@ -vendor device 驱动编写 -=========================== - -本节主要介绍如何编写一个 vendor device 驱动。 - -- 首先复制一份 class/template/usbd_xxx.c 文件 -- 实现以下三个回调函数,通常来说,vendor 驱动只需要实现 vendor_handler - -.. code-block:: C - - intf->class_interface_handler = xxx_class_interface_request_handler; - intf->class_endpoint_handler = NULL; - intf->vendor_handler = NULL; - intf->notify_handler = xxx_notify_handler; - -- 举例如下 - -case1 演示对于主机 IN 数据的处理,将数据拷贝到 *data 中,并指定*len 的长度。协议栈会自动发送给主机,不需要用户手动调用发送 API。 - -case2 演示对于主机 OUT 数据的处理,当执行到此函数时,说明数据都已经接收完成,可以直接读取 *data 中的数据,长度为 *len。 - -.. code-block:: C - - static int xxx_vendor_request_handler(uint8_t busid, struct usb_setup_packet *setup, uint8_t **data, uint32_t *len) - { - USB_LOG_WRN("XXX Class request: " - "bRequest 0x%02x\r\n", - setup->bRequest); - - switch (setup->bRequest) { - case 1: - memcpy(*data, xxx, sizeof(xxx)); - *len = sizeof(xxx); - case 2: - hexdump(*data, *len); - default: - USB_LOG_WRN("Unhandled XXX Class bRequest 0x%02x\r\n", setup->bRequest); - return -1; - } - - return 0; - } - -- 最后使用形如 usbd_add_interface(busid, usbd_xxx_init_intf(&intf)) 注册接口 \ No newline at end of file diff --git a/docs/source/demo/usbd_video.rst b/docs/source/demo/usbd_video.rst deleted file mode 100644 index e215abde..00000000 --- a/docs/source/demo/usbd_video.rst +++ /dev/null @@ -1,83 +0,0 @@ -usbd_video -=============== - -本节主要演示 USB UAC 功能,支持 YUYV, MJPEG, H264 格式。为了方便演示,都采用的静态图。 - -demo 包含 **video_static_yuyv_template**, **video_static_mjpeg_template**, **video_static_h264_template**, 仅描述符和图片数据不同。 - -- 在高速模式下,默认最大是1024字节,但是如果芯片支持 additional transcations,可以配置为最高 2048字节或者3072字节,这样可以提高传输效率。 - -.. code-block:: C - - #ifdef CONFIG_USB_HS - #define MAX_PAYLOAD_SIZE 1024 // for high speed with one transcations every one micro frame - #define VIDEO_PACKET_SIZE (unsigned int)(((MAX_PAYLOAD_SIZE / 1)) | (0x00 << 11)) - - // #define MAX_PAYLOAD_SIZE 2048 // for high speed with two transcations every one micro frame - // #define VIDEO_PACKET_SIZE (unsigned int)(((MAX_PAYLOAD_SIZE / 2)) | (0x01 << 11)) - - // #define MAX_PAYLOAD_SIZE 3072 // for high speed with three transcations every one micro frame - // #define VIDEO_PACKET_SIZE (unsigned int)(((MAX_PAYLOAD_SIZE / 3)) | (0x02 << 11)) - - #else - #define MAX_PAYLOAD_SIZE 1020 - #define VIDEO_PACKET_SIZE (unsigned int)(((MAX_PAYLOAD_SIZE / 1)) | (0x00 << 11)) - #endif - -- 通常只需要修改 WIDTH 和 HEIGHT - -.. code-block:: C - - #define WIDTH (unsigned int)(640) - #define HEIGHT (unsigned int)(480) - - #define CAM_FPS (30) - #define INTERVAL (unsigned long)(10000000 / CAM_FPS) - #define MIN_BIT_RATE (unsigned long)(WIDTH * HEIGHT * 16 * CAM_FPS) //16 bit - #define MAX_BIT_RATE (unsigned long)(WIDTH * HEIGHT * 16 * CAM_FPS) - #define MAX_FRAME_SIZE (unsigned long)(WIDTH * HEIGHT * 2) - -- USB 端点配置,默认 interval 为 1,也就是全速模式下 1ms,高速模式下 125us。同步类型使用异步模式。 - -.. code-block:: C - - /* 1.2.2.2 Standard VideoStream Isochronous Video Data Endpoint Descriptor */ - USB_ENDPOINT_DESCRIPTOR_INIT(VIDEO_IN_EP, 0x05, VIDEO_PACKET_SIZE, 0x01), - - -- 使用 `usbd_video_stream_start_write` 传输数据, 最后 **do_copy** 选项表示是否将数据 copy 到 packet_buffer, -如果不选择 copy, 则会直接在原图像数据中填充头部信息,并直接发送,达到 zero copy 功能。 - -- 因为提供的是静态数据,不能被修改,因此需要重新给一个 frame_buffer 用于图像传输,在实际对接 camera 场景中是动态数据,直接使用 camera 的数据缓冲区即可。 - - -.. code-block:: C - - void usbd_video_iso_callback(uint8_t busid, uint8_t ep, uint32_t nbytes) - { - if (usbd_video_stream_split_transfer(busid, ep)) { - /* one frame has done */ - iso_tx_busy = false; - } - } - - USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t packet_buffer[MAX_PAYLOAD_SIZE]; - USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t frame_buffer[32 * 1024]; - - void video_test(uint8_t busid) - { - memset(packet_buffer, 0, sizeof(packet_buffer)); - - while (1) { - if (tx_flag) { - iso_tx_busy = true; - memcpy(frame_buffer, cherryusb_mjpeg, sizeof(cherryusb_mjpeg)); // cherryusb_mjpeg is a static MJPEG frame buffer, so we need copy it to frame_buffer - usbd_video_stream_start_write(busid, VIDEO_IN_EP, packet_buffer, (uint8_t *)frame_buffer, sizeof(cherryusb_mjpeg), false); - while (iso_tx_busy) { - if (tx_flag == 0) { - break; - } - } - } - } - } \ No newline at end of file diff --git a/docs/source/demo/usbd_webusb.rst b/docs/source/demo/usbd_webusb.rst deleted file mode 100644 index 0df9bef6..00000000 --- a/docs/source/demo/usbd_webusb.rst +++ /dev/null @@ -1,21 +0,0 @@ -usbd_webusb -=============== - -本 demo 主要演示 webusb 功能,webusb 主要用于弹出网页并对 USB 设备进行访问。示例使用 webusb_hid_template.c。 - -- 在注册描述符时注册 BOS, MSOSV2, WEBUSB 描述符即可。 - -.. code-block:: C - - usbd_bos_desc_register(busid, &bos_desc); - usbd_msosv2_desc_register(busid, &msosv2_desc); - usbd_webusb_desc_register(busid, &webusb_url_desc); - -- 增加一个接口描述符用于 webusb - -.. code-block:: C - - USB_INTERFACE_DESCRIPTOR_INIT(USBD_WEBUSB_INTF_NUM, 0x00, 0x00, 0xff, 0x00, 0x00, 0x00) - -- 其余使用 hid 描述符,不再赘述 -- 枚举完成后,电脑右下角会弹出网页信息,点击即可打开网页 \ No newline at end of file diff --git a/docs/source/demo/usbd_winusb.rst b/docs/source/demo/usbd_winusb.rst deleted file mode 100644 index 0a6d4de9..00000000 --- a/docs/source/demo/usbd_winusb.rst +++ /dev/null @@ -1,55 +0,0 @@ -usbd_winusb -=============== - -本节主要介绍 winusb 驱动。winusb 是 windows 为了让用户友好的访问 USB 自定义类设备提供的一套通用驱动,其实本质就是 CDC ACM,只不过没有设置波特率的命令。 -WINUSB 版本根据 USB 版本分为 V1/V2 版本,V2 版本需要包含 BOS 描述符,V1 版本不需要。 **V2 版本需要在设备描述符中设置为 USB2.1 的版本号**。 - -.. note:: 更换 winusb 描述符任意配置可能会枚举成功但是无法识别设备,需要删除 计算机\HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\usbflags 下所有注册表项,重新插拔设备后生效。 - -- V1 版本注册描述符 - -.. code-block:: C - - const struct usb_descriptor winusbv1_descriptor = { - .device_descriptor_callback = device_descriptor_callback, - .config_descriptor_callback = config_descriptor_callback, - .device_quality_descriptor_callback = device_quality_descriptor_callback, - .string_descriptor_callback = string_descriptor_callback, - .msosv1_descriptor = &msosv1_desc - }; - - OR - - usbd_msosv1_desc_register(busid, &msosv1_desc); - -- V2 版本注册描述符 - -.. code-block:: C - - const struct usb_descriptor winusbv2_descriptor = { - .device_descriptor_callback = device_descriptor_callback, - .config_descriptor_callback = config_descriptor_callback, - .device_quality_descriptor_callback = device_quality_descriptor_callback, - .string_descriptor_callback = string_descriptor_callback, - .msosv2_descriptor = &msosv2_desc, - .bos_descriptor = &bos_desc, - }; - - OR - - usbd_bos_desc_register(busid, &bos_desc); - usbd_msosv2_desc_register(busid, &msosv2_desc); - - -- 接口描述符注册 - -.. code-block:: C - - /* Interface 0 */ - USB_INTERFACE_DESCRIPTOR_INIT(0x00, 0x00, 0x02, 0xFF, 0x00, 0x00, 0x02), - /* Endpoint OUT 2 */ - USB_ENDPOINT_DESCRIPTOR_INIT(WINUSB_OUT_EP, USB_ENDPOINT_TYPE_BULK, WINUSB_EP_MPS, 0x00), - /* Endpoint IN 1 */ - USB_ENDPOINT_DESCRIPTOR_INIT(WINUSB_IN_EP, USB_ENDPOINT_TYPE_BULK, WINUSB_EP_MPS, 0x00), - -- 读写操作与 CDC ACM 相同,不再赘述 \ No newline at end of file diff --git a/docs/source/demo/usbh_bluetooth.rst b/docs/source/demo/usbh_bluetooth.rst deleted file mode 100644 index a93844ea..00000000 --- a/docs/source/demo/usbh_bluetooth.rst +++ /dev/null @@ -1,2 +0,0 @@ -usbh_bluetooth -=============== diff --git a/docs/source/demo/usbh_hid.rst b/docs/source/demo/usbh_hid.rst deleted file mode 100644 index 6d519319..00000000 --- a/docs/source/demo/usbh_hid.rst +++ /dev/null @@ -1,55 +0,0 @@ -usbh_hid -=============== - -本节主要介绍 HID 类的使用。 - -- HID 枚举完成回调中创建一次性线程 - -.. code-block:: C - - - void usbh_hid_run(struct usbh_hid *hid_class) - { - usb_osal_thread_create("usbh_hid", 2048, CONFIG_USBHOST_PSC_PRIO + 1, usbh_hid_thread, hid_class); - } - - void usbh_hid_stop(struct usbh_hid *hid_class) - { - } - - -- 这里我们使用 usbh_submit_urb 的异步操作,在中断中处理数据并继续接收下一次数据。 - -.. code-block:: C - - static void usbh_hid_thread(void *argument) - { - int ret; - struct usbh_hid *hid_class = (struct usbh_hid *)argument; - ; - - /* test with only one buffer, if you have more hid class, modify by yourself */ - - /* Suggest you to use timer for int transfer and use ep interval */ - usbh_int_urb_fill(&hid_class->intin_urb, hid_class->hport, hid_class->intin, hid_buffer, hid_class->intin->wMaxPacketSize, 0, usbh_hid_callback, hid_class); - ret = usbh_submit_urb(&hid_class->intin_urb); - if (ret < 0) { - goto delete; - } - // clang-format off - delete: - usb_osal_thread_delete(NULL); - // clang-format on - } - -- 当然,也可以不使用异步操作,而是使用 timeout 的同步操作。 -- HID 使用的是中断传输,因此正常来说,我们需要根据 **bInterval** 来设置定时器,定时触发中断传输,demo 这里没有使用,如果对时间有精确要求,可以选择使用定时器来触发异步发送。 -- 以 hub 通信为例,采用的是一次性定时器,也可以使用周期性定时器。 - -.. code-block:: C - - hub->int_timer = usb_osal_timer_create("hubint_tim", USBH_GET_URB_INTERVAL(hub->intin->bInterval, hport->speed) / 1000, hub_int_timeout, hub, 0); - -.. note:: - - 这里的 `USBH_GET_URB_INTERVAL` 是一个宏定义,用于根据 binterval 计算 URB 的传输间隔时间, 单位是 us,而定时器最低是 ms ,因此需要除以 1000。对于小于等于 1ms 的不需要使用定时器。 \ No newline at end of file diff --git a/docs/source/demo/usbh_msc.rst b/docs/source/demo/usbh_msc.rst deleted file mode 100644 index 83956cc2..00000000 --- a/docs/source/demo/usbh_msc.rst +++ /dev/null @@ -1,56 +0,0 @@ -usbh_msc -=============== - -本节主要介绍主机 MSC 使用。借助 FATFS 实现读写功能。 - -- 在 msc 枚举完成的回调中注册一个线程,用于读写操作。 - -.. code-block:: C - - void usbh_msc_run(struct usbh_msc *msc_class) - { - usb_osal_thread_create("usbh_msc", 2048, CONFIG_USBHOST_PSC_PRIO + 1, usbh_msc_thread, msc_class); - } - - void usbh_msc_stop(struct usbh_msc *msc_class) - { - } - - -- 不使用 fatfs,则直接使用 usbh_msc_scsi_read10 或者 usbh_msc_scsi_write10 函数进行读写操作。 -- 如果使用 fatfs,则需要在 usbh_msc_thread 中调用 fatfs 的接口进行读写操作。msc读写适配fatfs 参考 `platform/fatfs/usbh_fatfs.c` - -.. code-block:: C - - static void usbh_msc_thread(void *argument) - { - int ret; - struct usbh_msc *msc_class = (struct usbh_msc *)argument; - - /* test with only one buffer, if you have more msc class, modify by yourself */ - #if 1 - /* get the partition table */ - ret = usbh_msc_scsi_read10(msc_class, 0, partition_table, 1); - if (ret < 0) { - USB_LOG_RAW("scsi_read10 error,ret:%d\r\n", ret); - goto delete; - } - for (uint32_t i = 0; i < 512; i++) { - if (i % 16 == 0) { - USB_LOG_RAW("\r\n"); - } - USB_LOG_RAW("%02x ", partition_table[i]); - } - USB_LOG_RAW("\r\n"); - #endif - - #if TEST_USBH_MSC_FATFS - usb_msc_fatfs_test(); - #endif - // clang-format off - delete: - usb_osal_thread_delete(NULL); - // clang-format on - } - -- 最后处理完成或者失败后,删除线程。 \ No newline at end of file diff --git a/docs/source/demo/usbh_net.rst b/docs/source/demo/usbh_net.rst deleted file mode 100644 index 8757991e..00000000 --- a/docs/source/demo/usbh_net.rst +++ /dev/null @@ -1,156 +0,0 @@ -usbh_net -=============== - -本节主要介绍 USB 网卡的使用,当前已经支持和测试以下 USB 网卡: - -- 4G 网卡:EC20(ECM/RNDIS)、手机(RNDIS)、SIMCOM7600(RNDIS)、ML307R(RNDIS)、AIR780(RNDIS) - -.. caution:: 请注意,部分 4G 网卡默认不带自动拨号功能,请更换固件或者使用 AT 配置成自动拨号,否则无法获取 IP。 - -- USB 以太网卡:ASIX AX88772,REALTEK RTL8152 -- USB WIFI 网卡: 博流 BL616(RNDIS/ECM) - -USB 网卡相关的宏和文件 ------------------------- - -网卡相关的宏如下,主要用于根据不同的网络组件注册网卡驱动: - -.. code-block:: C - - // #define CONFIG_USBHOST_PLATFORM_CDC_ECM - // #define CONFIG_USBHOST_PLATFORM_CDC_RNDIS - // #define CONFIG_USBHOST_PLATFORM_CDC_NCM - // #define CONFIG_USBHOST_PLATFORM_ASIX - // #define CONFIG_USBHOST_PLATFORM_RTL8152 - -.. note:: 如果使用了 Kconfig 系统,上述宏自定生成,其他平台请手动定义。 - -USB 网卡传输层面已经对接好了相关网络组件,列举如下: - -- 自定义 OS + LWIP 请使用 **platform/lwip/usbh_lwip.c**,需要自行包含该文件,并使能上述相关的宏。并在初始化 USB 之前调用 `tcpip_init(NULL, NULL)` -- RT-THREAD + LWIP 请使用 **platform/rtthread/usbh_lwip.c**,在 Kconfig 中使能对应的网卡驱动后自动勾选该文件,勾选 rt-thread lwip以后自动调用 `tcpip_init(NULL, NULL)` -- ESP-IDF + LWIP 请使用 **platform/freertos/usbh_net.c**,在 Kconfig 中使能对应的网卡驱动后自动勾选该文件,并且在初始化 USB 之前调用 `esp_netif_init()` + `esp_event_loop_create_default()` -- NUTTX + NUTTX 网络组件 请使用 **platform/nuttx/usbh_net.c**,在 Kconfig 中使能对应的网卡驱动后自动勾选该文件,勾选网络组件以后自动调用 - -.. note:: 如果是自行添加代码,别忘了添加 USB 网卡驱动相关的源文件,例如 **class/usbh_cdc_ecm.c**。所以我们推荐搭配对应平台使用哦,省去自己添加文件的麻烦 - -USB 网卡对接过程 -------------------- - -下面举例对接 LWIP 的对接过程。 - -- 在 USB 网卡枚举完成以后,会 **自动** 调用 `usbh_xxx_run` 函数,此时注册 netif 驱动,并且开启 DHCP 客户端和获取 IP 的定时器。 - -.. code-block:: C - - void usbh_cdc_ecm_run(struct usbh_cdc_ecm *cdc_ecm_class) - { - struct netif *netif = &g_cdc_ecm_netif; - - netif->hwaddr_len = 6; - memcpy(netif->hwaddr, cdc_ecm_class->mac, 6); - - IP4_ADDR(&g_ipaddr, 0, 0, 0, 0); - IP4_ADDR(&g_netmask, 0, 0, 0, 0); - IP4_ADDR(&g_gateway, 0, 0, 0, 0); - - netif = netif_add(netif, &g_ipaddr, &g_netmask, &g_gateway, NULL, usbh_cdc_ecm_if_init, tcpip_input); - netif_set_default(netif); - while (!netif_is_up(netif)) { - } - - dhcp_handle = usb_osal_timer_create("dhcp", 200, dhcp_timeout, netif, true); - if (dhcp_handle == NULL) { - USB_LOG_ERR("timer creation failed! \r\n"); - while (1) { - } - } - - usb_osal_thread_create("usbh_cdc_ecm_rx", 2048, CONFIG_USBHOST_PSC_PRIO + 1, usbh_cdc_ecm_rx_thread, NULL); - #if LWIP_DHCP - dhcp_start(netif); - usb_osal_timer_start(dhcp_handle); - #endif - } - -- `usbh_lwip_eth_output_common` 用于将发送 pbuf 组装成 USB 网卡数据包 -- `usbh_lwip_eth_input_common` 用于将 USB 网卡数据组装成 pbuf -- 实际网卡发送和接收处理 - -.. code-block:: C - - static err_t usbh_cdc_ecm_linkoutput(struct netif *netif, struct pbuf *p) - { - int ret; - (void)netif; - - usbh_lwip_eth_output_common(p, usbh_cdc_ecm_get_eth_txbuf()); - ret = usbh_cdc_ecm_eth_output(p->tot_len); - if (ret < 0) { - return ERR_BUF; - } else { - return ERR_OK; - } - } - - void usbh_cdc_ecm_eth_input(uint8_t *buf, uint32_t buflen) - { - usbh_lwip_eth_input_common(&g_cdc_ecm_netif, buf, buflen); - } - -- USB 网卡 拔出以后会 **自动** 调用 `usbh_xxx_stop` 函数,此时需要停止 DHCP 客户端,删除定时器,并且移除 netif。 - -.. code-block:: C - - void usbh_cdc_ecm_stop(struct usbh_cdc_ecm *cdc_ecm_class) - { - struct netif *netif = &g_cdc_ecm_netif; - (void)cdc_ecm_class; - - #if LWIP_DHCP - dhcp_stop(netif); - dhcp_cleanup(netif); - usb_osal_timer_delete(dhcp_handle); - #endif - netif_set_down(netif); - netif_remove(netif); - } - -- 因为 USB 网卡内部已经对接了LWIP,因此用户可以直接使用 LWIP 的 API,无需关心 USB 的实现。 - -USB 网卡 LWIP 配置宏相关注意事项 ------------------------------------- - -**LWIP_TCPIP_CORE_LOCKING_INPUT** 用于不使用 lwip 内置的 tcpip 线程,而使用 USB 自己的接收处理线程。 - -**LWIP_TCPIP_CORE_LOCKING** 在现在 lwip 版本中默认是打开的,也推荐必须打开。 - -**PBUF_POOL_BUFSIZE** 推荐大于1600,搭配 LWIP_TCPIP_CORE_LOCKING_INPUT 使用,因为我们提供了使用 zero mempy 的方式,使用静态 pbuf,而不是把数据 copy 到 pbuf 中。 - -**TCPIP_THREAD_STACKSIZE** 推荐大于 1K,防止栈溢出。 - -.. code-block:: C - - #if LWIP_TCPIP_CORE_LOCKING_INPUT != 1 - #warning suggest you to set LWIP_TCPIP_CORE_LOCKING_INPUT to 1, usb handles eth input with own thread - #endif - - #if LWIP_TCPIP_CORE_LOCKING != 1 - #error must set LWIP_TCPIP_CORE_LOCKING to 1 - #endif - - #if PBUF_POOL_BUFSIZE < 1600 - #error PBUF_POOL_BUFSIZE must be larger than 1600 - #endif - - #if TCPIP_THREAD_STACKSIZE < 1024 - #error TCPIP_THREAD_STACKSIZE must be >= 1024 - #endif - - -总结 --------------- - -.. note:: 通过以上内容,我们可以看到 CherryUSB 对 USB 网卡的支持是非常完善的,用户只需要使能对应的宏或者勾选,就可以实现 USB 网卡的自动识别和驱动注册,无需手动初始化网卡相关配置,用户只需关注应用层,极大地方便了用户的使用。 - -具体移植文章可以参考开发者的一些笔记 https://club.rt-thread.org/ask/article/5cf3e9e0b2d95800.html \ No newline at end of file diff --git a/docs/source/demo/usbh_serial.rst b/docs/source/demo/usbh_serial.rst deleted file mode 100644 index 619545c6..00000000 --- a/docs/source/demo/usbh_serial.rst +++ /dev/null @@ -1,196 +0,0 @@ -usbh_serial -=============== - -Serial 框架当前支持 cdc acm, ftdi, cp210x, ch34x, pl2303,gsm 驱动。 - -.. figure:: img/usbh_serial.png - -当前支持两种使用方式,一种是使用源生 CherryUSB usbhost serial API 进行操作,另一种是基于平台封装的 API 操作,比如 rt-thread device API,nuttx posix API。 - -下面演示的是使用 CherryUSB usbhost serial API 进行串口回环测试,并且使用阻塞发送,异步读取的方式: - -.. code-block:: C - - struct usbh_serial *serial; - - serial = usbh_serial_open("/dev/ttyACM0", USBH_SERIAL_O_RDWR | USBH_SERIAL_O_NONBLOCK); - if (serial == NULL) { - serial = usbh_serial_open("/dev/ttyUSB0", USBH_SERIAL_O_RDWR | USBH_SERIAL_O_NONBLOCK); - if (serial == NULL) { - USB_LOG_RAW("no serial device found\r\n"); - goto delete; - } - } - - struct usbh_serial_termios termios; - - memset(&termios, 0, sizeof(termios)); - termios.baudrate = 115200; - termios.stopbits = 0; - termios.parity = 0; - termios.databits = 8; - termios.rtscts = false; - termios.rx_timeout = 0; - ret = usbh_serial_control(serial, USBH_SERIAL_CMD_SET_ATTR, &termios); - if (ret < 0) { - USB_LOG_RAW("set serial attr error, ret:%d\r\n", ret); - goto delete_with_close; - } - - serial_tx_bytes = 0; - while (1) { - ret = usbh_serial_write(serial, serial_tx_buffer, sizeof(serial_tx_buffer)); - if (ret < 0) { - USB_LOG_RAW("serial write error, ret:%d\r\n", ret); - goto delete_with_close; - } else { - serial_tx_bytes += ret; - - if (serial_tx_bytes == SERIAL_TEST_LEN) { - USB_LOG_RAW("send over\r\n"); - break; - } - } - } - - volatile uint32_t wait_timeout = 0; - serial_rx_bytes = 0; - while (1) { - ret = usbh_serial_read(serial, &serial_rx_data[serial_rx_bytes], SERIAL_TEST_LEN - serial_rx_bytes); - if (ret < 0) { - USB_LOG_RAW("serial read error, ret:%d\r\n", ret); - goto delete_with_close; - } else { - serial_rx_bytes += ret; - - if (serial_rx_bytes == SERIAL_TEST_LEN) { - USB_LOG_RAW("receive over\r\n"); - for (uint32_t i = 0; i < SERIAL_TEST_LEN; i++) { - if (serial_rx_data[i] != 0xa5) { - USB_LOG_RAW("serial loopback data error at index %d, data: 0x%02x\r\n", (unsigned int)i, serial_rx_data[i]); - goto delete_with_close; - } - } - serial_test_success = true; - break; - } - } - wait_timeout++; - - if (wait_timeout > 500) { // 5s - USB_LOG_RAW("serial read timeout\r\n"); - goto delete_with_close; - } - - usb_osal_msleep(10); - } - - usbh_serial_close(serial); - -.. caution:: 需要注意,例程中使用的是比较简单的先发送后读取的方式,因此发送的总长度不可以超过 CONFIG_USBHOST_SERIAL_RX_SIZE,正常使用 TX/RX 请分开进行。 - -用户需要考虑以下三种场景: - -- USB2TTL 设备 + 启用了波特率(USB2TTL设备必须启用波特率),这种情况下需要使用 `usbh_serial_write` 和 `usbh_serial_read` 进行收发数据, **并且 read 操作需要及时,防止 ringbuf 数据溢出而丢包**。不可以使用 `usbh_serial_cdc_write_async` 和 `usbh_serial_cdc_read_async` - -- 纯 USB 设备 + 未启动波特率,这种情况下可以使用 `usbh_serial_cdc_write_async` 和 `usbh_serial_cdc_read_async` 进行异步收发数据。阻塞则可以用 `usbh_serial_write` ,不可以使用 `usbh_serial_read`。 - -- 纯 USB 设备 + 启动波特率,同 1,但是接收速率会打折扣(因为多了一层 ringbuf)。此时也不可以使用 `usbh_serial_cdc_write_async` 和 `usbh_serial_cdc_read_async`。 **如果是 GSM 设备请使用第一种场景**。 - -.. note:: 简单来说就是,如果接收数据需要用到ringbuf转一层的,请使用第一种场景。 - -.. code-block:: C - - [I/usbh_hub] New full-speed device on Bus 0, Hub 1, Port 1 connected - [I/usbh_core] New device found,idVendor:10c4,idProduct:ea60,bcdDevice:0100 - [I/usbh_core] The device has 1 bNumConfigurations - [I/usbh_core] The device has 1 interfaces - [I/usbh_core] Enumeration success, start loading class driver - [I/usbh_core] Loading cp210x class driver on interface 0 - [I/usbh_cp210x] chip partnum: 0x02 - [I/usbh_cp210x] ulAmountInInQueue: 0, ulAmountInOutQueue: 0 - [I/usbh_serial] Ep=81 Attr=02 Mps=64 Interval=00 Mult=00 - [I/usbh_serial] Ep=01 Attr=02 Mps=64 Interval=00 Mult=00 - [I/usbh_serial] Register Serial Class: /dev/ttyUSB0 (cp210x) - start serial loopback test, len: 1024 - send over - receive over - serial loopback test success - [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB0 (cp210x) - [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected - [I/usbh_hub] New high-speed device on Bus 0, Hub 1, Port 1 connected - [I/usbh_core] New device found,idVendor:0403,idProduct:6010,bcdDevice:0700 - [I/usbh_core] The device has 1 bNumConfigurations - [I/usbh_core] The device has 2 interfaces - [I/usbh_core] Enumeration success, start loading class driver - [I/usbh_core] Loading ftdi class driver on interface 0 - [I/usbh_ftdi] chip name: FT2232H - [I/usbh_serial] Ep=81 Attr=02 Mps=512 Interval=00 Mult=00 - [I/usbh_serial] Ep=02 Attr=02 Mps=512 Interval=00 Mult=00 - [I/usbh_serial] Register Serial Class: /dev/ttyUSB0 (ftdi) - [I/usbh_core] Loading ftdi class driver on interface 1 - [I/usbh_ftdi] chip name: FT2232H - [I/usbh_serial] Ep=83 Attr=02 Mps=512 Interval=00 Mult=00 - [I/usbh_serial] Ep=04 Attr=02 Mps=512 Interval=00 Mult=00 - [I/usbh_serial] Register Serial Class: /dev/ttyUSB1 (ftdi) - start serial loopback test, len: 1024 - send over - receive over - serial loopback test success - [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB0 (ftdi) - [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB1 (ftdi) - [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected - [I/usbh_hub] New full-speed device on Bus 0, Hub 1, Port 1 connected - [I/usbh_core] New device found,idVendor:067b,idProduct:2303,bcdDevice:0300 - [I/usbh_core] The device has 1 bNumConfigurations - [I/usbh_core] The device has 1 interfaces - [I/usbh_core] Enumeration success, start loading class driver - [I/usbh_core] Loading pl2303 class driver on interface 0 - [I/usbh_pl2303] Ep=81 Attr=03 Mps=10 Interval=01 Mult=00 - [I/usbh_pl2303] chip type: PL2303HX - [I/usbh_serial] Ep=02 Attr=02 Mps=64 Interval=00 Mult=00 - [I/usbh_serial] Ep=83 Attr=02 Mps=64 Interval=00 Mult=00 - [I/usbh_serial] Register Serial Class: /dev/ttyUSB0 (pl2303) - start serial loopback test, len: 1024 - send over - receive over - serial loopback test success - [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB0 (pl2303) - [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected - [W/usbh_hub] Failed to enable port 1 - [I/usbh_hub] New full-speed device on Bus 0, Hub 1, Port 1 connected - [I/usbh_core] New device found,idVendor:1a86,idProduct:7523,bcdDevice:0264 - [I/usbh_core] The device has 1 bNumConfigurations - [I/usbh_core] The device has 1 interfaces - [I/usbh_core] Enumeration success, start loading class driver - [I/usbh_core] Loading ch34x class driver on interface 0 - [I/usbh_ch43x] Ep=81 Attr=03 Mps=8 Interval=01 Mult=00 - [I/usbh_ch43x] chip version: 0x31 - [I/usbh_serial] Ep=82 Attr=02 Mps=32 Interval=00 Mult=00 - [I/usbh_serial] Ep=02 Attr=02 Mps=32 Interval=00 Mult=00 - [I/usbh_serial] Register Serial Class: /dev/ttyUSB0 (ch34x) - start serial loopback test, len: 1024 - send over - receive over - serial loopback test success - [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB0 (ch34x) - [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected - [I/usbh_hub] New full-speed device on Bus 0, Hub 1, Port 1 connected - [I/usbh_core] New device found,idVendor:42bf,idProduct:b210,bcdDevice:0217 - [I/usbh_core] The device has 1 bNumConfigurations - [I/usbh_core] The device has 3 interfaces - [I/usbh_core] Enumeration success, start loading class driver - [E/usbh_core] Do not support Class:0xff, Subclass:0x01, Protocl:0x00 on interface 0 - [I/usbh_core] Loading cdc_acm class driver on interface 1 - [I/usbh_cdc_acm] Ep=85 Attr=03 Mps=64 Interval=00 Mult=00 - [I/usbh_serial] Ep=04 Attr=02 Mps=64 Interval=00 Mult=00 - [I/usbh_serial] Ep=83 Attr=02 Mps=64 Interval=00 Mult=00 - [I/usbh_serial] Register Serial Class: /dev/ttyACM0 (cdc_acm) - [I/usbh_core] Loading cdc_data class driver on interface 2 - start serial loopback test, len: 1024 - send over - receive over - serial loopback test success - [I/usbh_serial] Unregister Serial Class: /dev/ttyACM0 (cdc_acm) - [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected - diff --git a/docs/source/demo/usbh_vendor.rst b/docs/source/demo/usbh_vendor.rst deleted file mode 100644 index b86bda60..00000000 --- a/docs/source/demo/usbh_vendor.rst +++ /dev/null @@ -1,127 +0,0 @@ -vendor host 驱动编写 -=========================== - -本节主要介绍如何编写一个 vendor host 驱动。 - -- 首先复制一份 class/template/usbh_xxx.c 文件 - -- 定义 class 驱动并使用 CLASS_INFO_DEFINE 前缀,这样,枚举完成后,协议栈自动通过 usbd_class_find_driver 来查找对应的驱动。 - -.. code-block:: C - - static const struct usbh_class_driver xxx_class_driver = { - .driver_name = "xxx", - .connect = usbh_xxx_connect, - .disconnect = usbh_xxx_disconnect - }; - - CLASS_INFO_DEFINE const struct usbh_class_info xxx_class_info = { - .match_flags = USB_CLASS_MATCH_INTF_CLASS | USB_CLASS_MATCH_INTF_SUBCLASS | USB_CLASS_MATCH_INTF_PROTOCOL, - .bInterfaceClass = 0, - .bInterfaceSubClass = 0, - .bInterfaceProtocol = 0, - .id_table = NULL, - .class_driver = &xxx_class_driver - }; - - -- 实现 connect 和 disconnect 函数, 在 connect 函数中,需要分配一个 xxx_class 结构体,在 disconnect 函数中释放 urb 和 xxx_class。 - -.. code-block:: C - - struct usbh_xxx { - struct usbh_hubport *hport; - struct usb_endpoint_descriptor *xxxin; - struct usb_endpoint_descriptor *xxxout; - struct usbh_urb xxxin_urb; - struct usbh_urb xxxout_urb; - - uint8_t intf; /* interface number */ - uint8_t minor; - - void *user_data; - }; - - static int usbh_xxx_connect(struct usbh_hubport *hport, uint8_t intf) - { - struct usb_endpoint_descriptor *ep_desc; - int ret; - - struct usbh_xxx *xxx_class = usbh_xxx_class_alloc(); - if (xxx_class == NULL) { - USB_LOG_ERR("Fail to alloc xxx_class\r\n"); - return -USB_ERR_NOMEM; - } - - return ret; - } - - - static int usbh_xxx_disconnect(struct usbh_hubport *hport, uint8_t intf) - { - int ret = 0; - - struct usbh_xxx *xxx_class = (struct usbh_xxx *)hport->config.intf[intf].priv; - - if (xxx_class) { - if (xxx_class->xxxin) { - usbh_kill_urb(&xxx_class->xxxin_urb); - } - - if (xxx_class->xxxout) { - usbh_kill_urb(&xxx_class->xxxout_urb); - } - - if (hport->config.intf[intf].devname[0] != '\0') { - USB_LOG_INFO("Unregister xxx Class:%s\r\n", hport->config.intf[intf].devname); - usbh_xxx_stop(xxx_class); - } - - usbh_xxx_class_free(xxx_class); - } - - return ret; - } - -- 初始化端点 - -.. code-block:: C - - for (uint8_t i = 0; i < hport->config.intf[intf].altsetting[0].intf_desc.bNumEndpoints; i++) { - ep_desc = &hport->config.intf[intf].altsetting[0].ep[i].ep_desc; - if (ep_desc->bEndpointAddress & 0x80) { - USBH_EP_INIT(xxx_class->intin, ep_desc); - } else { - USBH_EP_INIT(xxx_class->intout, ep_desc); - } - } - -- 最后设计收发 API,根据实际情况设计成同步 or 异步。 - -.. code-block:: C - - int usbh_xxx_in_transfer(struct usbh_xxx *xxx_class, uint8_t *buffer, uint32_t buflen, uint32_t timeout) - { - int ret; - struct usbh_urb *urb = &xxx_class->xxxin_urb; - - usbh_xxx_urb_fill(urb, xxx_class->hport, xxx_class->xxxin, buffer, buflen, timeout, NULL, NULL); - ret = usbh_submit_urb(urb); - if (ret == 0) { - ret = urb->actual_length; - } - return ret; - } - - int usbh_xxx_out_transfer(struct usbh_xxx *xxx_class, uint8_t *buffer, uint32_t buflen, uint32_t timeout) - { - int ret; - struct usbh_urb *urb = &xxx_class->xxxout_urb; - - usbh_xxx_urb_fill(urb, xxx_class->hport, xxx_class->xxxout, buffer, buflen, timeout, NULL, NULL); - ret = usbh_submit_urb(urb); - if (ret == 0) { - ret = urb->actual_length; - } - return ret; - } \ No newline at end of file diff --git a/docs/source/demo/usbh_wifi.rst b/docs/source/demo/usbh_wifi.rst deleted file mode 100644 index be148c7d..00000000 --- a/docs/source/demo/usbh_wifi.rst +++ /dev/null @@ -1,2 +0,0 @@ -usbh_wifi -=============== diff --git a/docs/source/index.rst b/docs/source/index.rst deleted file mode 100644 index 831de0a1..00000000 --- a/docs/source/index.rst +++ /dev/null @@ -1,157 +0,0 @@ -.. CherryUSB 使用指南 documentation master file, created by - sphinx-quickstart on Thu Nov 21 10:50:33 2019. - You can adapt this file completely to your liking, but it should at least - contain the root `toctree` directive. - -CherryUSB 使用指南 -====================================================== - -CherryUSB 是一个小而美的、可移植性高的、用于嵌入式系统的 USB 主从协议栈。同时 CherryUSB 具有以下优点: - -**易于学习 USB** - -为了方便用户学习 USB 基本知识、枚举、驱动加载、IP 驱动,因此,编写的代码具备以下优点: - -- 代码精简,逻辑简单,无复杂 C 语言语法 -- 树状化编程,代码层层递进 -- Class 驱动和 porting 驱动模板化、精简化 -- API 分类清晰(从机:初始化、注册类、命令回调类、数据收发类;主机:初始化、查找类、数据收发类) - -**易于使用 USB** - -为了方便用户使用 USB 接口,考虑到用户学习过 uart 和 dma,因此,设计的数据收发类接口具备以下优点: - -- 等价于使用 uart tx dma/uart rx dma -- 收发长度没有限制,用户不需要关心 USB 分包过程(porting 驱动做分包过程) - -**易于发挥 USB 性能** - -考虑到 USB 性能问题,尽量达到 USB 硬件理论带宽,因此,设计的数据收发类接口具备以下优点: - -- Porting 驱动直接对接寄存器,无抽象层封装 -- Memory zero copy -- IP 如果带 DMA 则使用 DMA 模式(DMA 带硬件分包功能) -- 长度无限制,方便对接硬件 DMA 并且发挥 DMA 的优势 -- 分包功能在中断中处理 - -**从机协议栈整体执行流程** - -.. figure:: usbdev.svg - -**主机协议栈整体执行流程** - -.. figure:: usbhost.svg - -**其他相关链接** - -- **视频教程**: https://www.bilibili.com/cheese/play/ss707687201 -- **github** : https://github.com/sakumisu/CherryUSB -- **CherryUSB原理性分析和应用实践-汉斯期刊**: https://www.hanspub.org/journal/paperinformation?paperid=126903 - -.. toctree:: - :maxdepth: 1 - :caption: 快速上手 - - quick_start/start - quick_start/demo - quick_start/transplant - quick_start/rtthread - quick_start/q&a - quick_start/migration - quick_start/share - quick_start/opensource - -.. toctree:: - :maxdepth: 1 - :caption: USB 基本知识点 - - usb/usb2.0_basic - usb/usb3.0_basic - usb/usb_desc - usb/usb_request - usb/usb_enum - usb/usb_ext - -.. toctree:: - :maxdepth: 1 - :caption: API 手册 - - api/api_device - api/api_host - api/api_port - api/api_config - -.. toctree:: - :maxdepth: 1 - :caption: Class 指南 - - class/class_cdc - class/class_hid - class/class_msc - class/class_audio - class/class_video - class/winusb - -.. toctree:: - :maxdepth: 1 - :caption: 例程说明 - - demo/usbd_cdc_acm - demo/usbd_hid - demo/usbd_msc - demo/usbd_rndis - demo/usbd_ecm - demo/usbd_audiov1 - demo/usbd_audiov2 - demo/usbd_video - demo/usbd_winusb - demo/usbd_webusb - demo/usbd_adb - demo/usbh_serial - demo/usbh_hid - demo/usbh_msc - demo/usbh_net - demo/usbh_bluetooth - demo/usbh_wifi - demo/usbd_vendor - demo/usbh_vendor - demo/usb_otg - -.. toctree:: - :maxdepth: 1 - :caption: USBIP 介绍 - - usbip/ohci - usbip/ehci - usbip/xhci - usbip/chipidea - usbip/dwc2 - usbip/musb - usbip/fotg210 - usbip/cdns2 - usbip/cdns3 - usbip/dwc3 - -.. toctree:: - :maxdepth: 1 - :caption: 工具使用 - - tools/index - -.. toctree:: - :maxdepth: 1 - :caption: 版本说明 - - version - -.. toctree:: - :maxdepth: 1 - :caption: 性能展示 - - show/index - -.. toctree:: - :maxdepth: 1 - :caption: 商业支持 - - support/index \ No newline at end of file diff --git a/docs/source/quick_start/demo.rst b/docs/source/quick_start/demo.rst deleted file mode 100644 index e51a2e3e..00000000 --- a/docs/source/quick_start/demo.rst +++ /dev/null @@ -1,224 +0,0 @@ -基于现有 demo 快速验证 -========================= - -在学习 USB 或者是学习 CherryUSB 代码之前,我们需要先基于现有的 demo 进行快速验证,为什么?是为了提升对 USB 的兴趣,能有信心进行下一步的动作,如果 demo 都跑不起来,或者自己摸索写代码,或者先看 USB 基本概念,结果看到最后, -发现一点都看不懂,概念好多,根本记不住,从而丧失对 USB 的兴趣。因此,先跑 demo 非常重要。下面我将给大家罗列目前支持的 demo 仓库。 - -基于 bouffalolab 系列芯片(官方 SDK 支持) ------------------------------------------- - -仓库参考:https://github.com/CherryUSB/cherryusb_bouffalolab - -- BL616/BL808:USB2.0 内置 HS phy 芯片,支持主从机。device 支持 5 个端点(包括端点0),不支持双向同时使用。 -- USB 的相关应用位于 `examples/usbdev` 和 `examples/usbhost` 目录下,根据官方环境搭建完成后,即可编译使用。 - -基于 HPMicro 系列芯片(官方 SDK 支持) ------------------------------------------------------ - -仓库参考:https://github.com/CherryUSB/cherryusb_hpmicro - -- HPM 系列: USB2.0 内置 HS phy 芯片,支持主从机。device 支持 8/16 端点(包括端点0),并且可以同时使用双向,不同芯片个数有差异。 -- USB 的相关应用位于 `samples/cherryusb` ,根据官方环境搭建完成后,即可编译使用。 - -基于 esp32s2/s3/p4 系列芯片(官方 SDK 即将支持) -------------------------------------------------- - -仓库参考:https://github.com/CherryUSB/cherryusb_esp32 - -- esp32s2/s3:USB2.0 内置全速 PHY 芯片,支持主从机,device 支持 7 个端点(包括端点0),并且可以同时使用双向。 -- esp32p4:一个 USB2.0 内置全速 PHY 芯片,一个 USB2.0 内置高速 PHY 芯片,支持主从机。 -- 默认 demo 采用组件库安装的形式,在 https://components.espressif.com/ 中搜索 cherryusb 即可 - -ESP-Registry 可以参考官方文档,推荐使用 vscode + esp-idf 的开发环境。 - -- ctrl + shift + p 选择 ESP-IDF 欢迎界面,然后选择 Component mananger - -.. figure:: img/esp1.png - -- 找到 cherryusb 并安装 - -.. figure:: img/esp2.png - -- 打开 menuconfig,并打开 cherryusb 的配置,根据实际情况选择主机或者从机模式 - -.. figure:: img/esp3.png -.. figure:: img/esp4.png - -基于飞腾派系列芯片(官方 SDK 支持) ------------------------------------ - -仓库参考:https://gitee.com/phytium_embedded/phytium-free-rtos-sdk - -- 飞腾派支持两个 USB3.0 主机(采用 XHCI), 两个 USB2.0 主从机 -- USB 的相关应用位于 `example/peripheral/usb` ,根据官方环境搭建完成后,即可编译使用。 - -基于 Essemi 系列芯片(官方 SDK 支持) ------------------------------------------ - -仓库参考:https://github.com/CherryUSB/cherryusb_es32 - -- 支持全速和高速主从机。device 支持 6 个端点(包括端点0),并且可以同时使用双向。 - -基于 Artinchip 系列芯片(官方 SDK 支持) ------------------------------------------------ - -仓库参考:https://gitee.com/artinchip/luban-lite - -- 支持全速和高速主从机,主机采用 EHCI + OHCI。device 支持 8 个端点(包括端点0),并且可以同时使用双向。 - -基于 canmv-k230 芯片(官方 SDK 支持) ---------------------------------------------- - -仓库参考:https://github.com/CherryUSB/k230_sdk - -- K230: 两个 USB2.0 内置 HS PHY 芯片,支持主从机。device 支持 16 个端点(包括端点0),并且可以同时使用双向。 - -基于 NXP MCX系列芯片 ---------------------------- - -仓库参考:https://github.com/CherryUSB/cherryusb_mcx 或者 https://github.com/RT-Thread/rt-thread/tree/master/bsp/nxp/mcx - -- 支持全速 IP 和高速 IP, 高速 IP 支持主机和从机。device 支持 8 个端点(包括端点0),并且可以同时使用双向。 - -基于 RP2040/RP2035 芯片(官方 SDK 即将支持) --------------------------------------------- - -仓库参考: https://github.com/CherryUSB/pico-examples 和 https://github.com/CherryUSB/pico-sdk - -基于 ST 系列芯片 ---------------------------- - -仓库参考:https://github.com/CherryUSB/cherryusb_stm32 - -默认提供以下 demo 工程: - -- F103 使用 fsdev ip -- F429 主从使用 USB1, 引脚 pb14/pb15, 默认从机没有开启 DMA 模式 -- H7 设备使用 USB0, 引脚 pa11/pa12,没有开 DMA 模式。主机使用 USB1 ,引脚 pb14/pb15,并且需要做 nocache 处理 - -demo 底下提供了 **stm32xxx.ioc** 文件,双击打开,点击 **Generate Code** 即可。 - -.. caution:: 生成完以后,请使用 git reset 功能将被覆盖的 `main.c` 和 `stm32xxx_it.c` 文件撤回,禁止被 cubemx 覆盖。 - -涵盖 F1/F4/H7,其余芯片基本类似,不再赘述,具体区别有: - -- usb ip 区别:F1使用 fsdev,F4/H7使用 dwc2 -- dwc2 ip 区别: USB0 (引脚是 PA11/PA12) 和 USB1 (引脚是 PB14/PB15), 其中 USB1 默认全速,可以接外部PHY 形成高速主机,并且带 dma 功能 -- F4 无 cache,H7 有 cache - -如果是 STM32F7/STM32H7 这种带 cache 功能,需要将 usb 使用到的 ram 定位到 no cache ram 区域。举例如下 - -.. code-block:: C - - cpu_mpu_config(0, MPU_Normal_NonCache, 0x24070000, MPU_REGION_SIZE_64KB); - -对应 keil 中的 sct 脚本修改: - -.. code-block:: C - - LR_IROM1 0x08000000 0x00200000 { ; load region size_region - ER_IROM1 0x08000000 0x00200000 { ; load address = execution address - *.o (RESET, +First) - *(InRoot$$Sections) - .ANY (+RO) - .ANY (+XO) - } - RW_IRAM2 0x24000000 0x00070000 { ; RW data - .ANY (+RW +ZI) - } - USB_NOCACHERAM 0x24070000 0x00010000 { ; RW data - *(.noncacheable) - } - } - -USB Device 移植要点 -^^^^^^^^^^^^^^^^^^^^^^ - -- 使用 **stm32cubemx** 创建工程,配置基本的 RCC、UART (作为log使用) - -.. figure:: img/stm32_1.png -.. figure:: img/stm32_2.png - -- 如果使用 fsdev ip,勾选 **USB** 。如果使用 dwc2 ip,勾选 **USB_OTG_FS** 或者勾选 **USB_OTG_HS**。开启 USB 中断,其他配置对我们没用,代码中不会使用任何 st 的 usb 库。 - -.. figure:: img/stm32_3_1.png -.. figure:: img/stm32_3_2.png - -- 配置 usb clock 为 48M - -.. figure:: img/stm32_4_1.png -.. figure:: img/stm32_4_2.png - -- 选择好工程,这里我们选择 keil,设置好 stack 和 heap,如果使用 msc 可以推荐设置大点,然后点击 **Generate Code**。 - -.. figure:: img/stm32_5.png - -- 添加 CherryUSB 必须要的源码( **usbd_core.c** 、 **dwc2/usb_dc_dwc2.c** 或者是 **fsdev/usb_dc_fsdev.c** ),以及想要使用的 class 驱动,可以将对应的 class template 添加方便测试。 - -.. figure:: img/stm32_6.png - -- 头文件该加的加 - -.. figure:: img/stm32_7.png - -- 复制一份 **cherryusb_config_template.h**,放到 `Core/Inc` 目录下,并命名为 `usb_config.h` - -.. figure:: img/stm32_8.png - -- 如果使用 fsdev ip,(V1.5.0 开始需要增加 **fsdev/usb_glue_st.c**) 在 `usb_config.h` 中实现以下宏,具体数值不同芯片不一样: - -.. code-block:: C - - #define CONFIG_USBDEV_FSDEV_PMA_ACCESS 2 - -- 编译器推荐使用 **AC6**。勾选 **Microlib**,并实现 **printf** ,方便后续查看 log。 - -.. figure:: img/stm32_10.png -.. figure:: img/stm32_11.png - -.. note :: 以下两个步骤从 V1.5.0 开始不再需要,**fsdev/usb_glue_st.c**, **dwc2/usb_glue_st.c** 文件中已经实现 - -- 拷贝 **xxx_msp.c** 中的 **HAL_PCD_MspInit** 函数中的内容到 **usb_dc_low_level_init** 函数中,屏蔽 st 生成的 usb 初始化 - -.. figure:: img/stm32_12.png -.. figure:: img/stm32_14.png - -- 在中断函数中调用 `USBD_IRQHandler`,并传入 `busid` - -.. figure:: img/stm32_13.png - -- 如果芯片带 cache,cache 修改参考 :ref:`usb_cache` 章节 - -- 调用 template 的内容初始化,并填入 `busid` 和 USB IP 的 `reg base`, `busid` 从 0 开始,不能超过 `CONFIG_USBDEV_MAX_BUS` - -.. figure:: img/stm32_15.png - -USB Host 移植要点 -^^^^^^^^^^^^^^^^^^^^^^ - -前面 6 步与 Device 一样。需要注意,host 驱动只支持带 dma 的 hs port (引脚是 PB14/PB15),所以 fs port (引脚是 PA11/PA12)不做支持(没有 dma 你玩什么主机)。 - -- 添加 CherryUSB 必须要的源码( **usbh_core.c** 、 **usbh_hub.c** 、 **usb_hc_dwc2.c** 、 **usb_glue_st.c** 以及 **osal** 目录下的适配层文件),以及想要使用的 class 驱动,并且可以将对应的 **usb host.c** 添加方便测试。 - -.. figure:: img/stm32_16.png - -- 编译器推荐使用 **AC6**。勾选 **Microlib**,并实现 **printf** ,方便后续查看 log。 - -.. figure:: img/stm32_10.png -.. figure:: img/stm32_11.png - -- 复制一份 **cherryusb_config_template.h**,放到 `Core/Inc` 目录下,并命名为 `usb_config.h` - -.. note :: 以下两个步骤从 V1.5.0 开始不再需要,**fsdev/usb_glue_st.c**, **dwc2/usb_glue_st.c** 文件中已经实现 - -- 拷贝 **xxx_msp.c** 中的 `HAL_HCD_MspInit` 函数中的内容到 `usb_hc_low_level_init` 函数中,屏蔽 st 生成的 usb 初始化 -- 在中断函数中调用 `USBH_IRQHandler`,并传入 `busid` - -.. figure:: img/stm32_19.png - -- 链接脚本修改参考 :ref:`usbh_link_script` 章节 -- 如果芯片带 cache,cache 修改参考 :ref:`usb_cache` 章节 -- 调用 `usbh_initialize` 并填入 `busid` 和 USB IP 的 `reg base` 还有 `event_handler` 可缺省为NULL, `busid` 从 0 开始,不能超过 `CONFIG_USBHOST_MAX_BUS` -- 启动线程 - -.. figure:: img/stm32_18.png diff --git a/docs/source/quick_start/img/env0.png b/docs/source/quick_start/img/env0.png deleted file mode 100644 index c0a8b03f..00000000 Binary files a/docs/source/quick_start/img/env0.png and /dev/null differ diff --git a/docs/source/quick_start/img/env1.png b/docs/source/quick_start/img/env1.png deleted file mode 100644 index 2a68e052..00000000 Binary files a/docs/source/quick_start/img/env1.png and /dev/null differ diff --git a/docs/source/quick_start/img/env2.png b/docs/source/quick_start/img/env2.png deleted file mode 100644 index ee37101a..00000000 Binary files a/docs/source/quick_start/img/env2.png and /dev/null differ diff --git a/docs/source/quick_start/img/esp1.png b/docs/source/quick_start/img/esp1.png deleted file mode 100644 index 1f059e71..00000000 Binary files a/docs/source/quick_start/img/esp1.png and /dev/null differ diff --git a/docs/source/quick_start/img/esp2.png b/docs/source/quick_start/img/esp2.png deleted file mode 100644 index fd20e9ce..00000000 Binary files a/docs/source/quick_start/img/esp2.png and /dev/null differ diff --git a/docs/source/quick_start/img/esp3.png b/docs/source/quick_start/img/esp3.png deleted file mode 100644 index 82a7162f..00000000 Binary files a/docs/source/quick_start/img/esp3.png and /dev/null differ diff --git a/docs/source/quick_start/img/esp4.png b/docs/source/quick_start/img/esp4.png deleted file mode 100644 index ffb2882a..00000000 Binary files a/docs/source/quick_start/img/esp4.png and /dev/null differ diff --git a/docs/source/quick_start/img/question1.png b/docs/source/quick_start/img/question1.png deleted file mode 100644 index a852e6aa..00000000 Binary files a/docs/source/quick_start/img/question1.png and /dev/null differ diff --git a/docs/source/quick_start/img/question2.png b/docs/source/quick_start/img/question2.png deleted file mode 100644 index e00b3bfa..00000000 Binary files a/docs/source/quick_start/img/question2.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_1.png b/docs/source/quick_start/img/stm32_1.png deleted file mode 100644 index b91044a5..00000000 Binary files a/docs/source/quick_start/img/stm32_1.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_10.png b/docs/source/quick_start/img/stm32_10.png deleted file mode 100644 index d55b38e7..00000000 Binary files a/docs/source/quick_start/img/stm32_10.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_11.png b/docs/source/quick_start/img/stm32_11.png deleted file mode 100644 index 3ad5b074..00000000 Binary files a/docs/source/quick_start/img/stm32_11.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_12.png b/docs/source/quick_start/img/stm32_12.png deleted file mode 100644 index 84aaffe8..00000000 Binary files a/docs/source/quick_start/img/stm32_12.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_13.png b/docs/source/quick_start/img/stm32_13.png deleted file mode 100644 index f12fad75..00000000 Binary files a/docs/source/quick_start/img/stm32_13.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_14.png b/docs/source/quick_start/img/stm32_14.png deleted file mode 100644 index e5aa5b19..00000000 Binary files a/docs/source/quick_start/img/stm32_14.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_15.png b/docs/source/quick_start/img/stm32_15.png deleted file mode 100644 index 7c293287..00000000 Binary files a/docs/source/quick_start/img/stm32_15.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_16.png b/docs/source/quick_start/img/stm32_16.png deleted file mode 100644 index 70f2e63c..00000000 Binary files a/docs/source/quick_start/img/stm32_16.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_18.png b/docs/source/quick_start/img/stm32_18.png deleted file mode 100644 index 456df189..00000000 Binary files a/docs/source/quick_start/img/stm32_18.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_19.png b/docs/source/quick_start/img/stm32_19.png deleted file mode 100644 index a796dc75..00000000 Binary files a/docs/source/quick_start/img/stm32_19.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_2.png b/docs/source/quick_start/img/stm32_2.png deleted file mode 100644 index 671b1b82..00000000 Binary files a/docs/source/quick_start/img/stm32_2.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_3_1.png b/docs/source/quick_start/img/stm32_3_1.png deleted file mode 100644 index 9e42196d..00000000 Binary files a/docs/source/quick_start/img/stm32_3_1.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_3_2.png b/docs/source/quick_start/img/stm32_3_2.png deleted file mode 100644 index 492d6739..00000000 Binary files a/docs/source/quick_start/img/stm32_3_2.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_4_1.png b/docs/source/quick_start/img/stm32_4_1.png deleted file mode 100644 index e81437bc..00000000 Binary files a/docs/source/quick_start/img/stm32_4_1.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_4_2.png b/docs/source/quick_start/img/stm32_4_2.png deleted file mode 100644 index dd90f5b8..00000000 Binary files a/docs/source/quick_start/img/stm32_4_2.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_5.png b/docs/source/quick_start/img/stm32_5.png deleted file mode 100644 index 5bec9878..00000000 Binary files a/docs/source/quick_start/img/stm32_5.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_6.png b/docs/source/quick_start/img/stm32_6.png deleted file mode 100644 index f0ad9a0b..00000000 Binary files a/docs/source/quick_start/img/stm32_6.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_7.png b/docs/source/quick_start/img/stm32_7.png deleted file mode 100644 index 8aef0bfa..00000000 Binary files a/docs/source/quick_start/img/stm32_7.png and /dev/null differ diff --git a/docs/source/quick_start/img/stm32_8.png b/docs/source/quick_start/img/stm32_8.png deleted file mode 100644 index 08d2e724..00000000 Binary files a/docs/source/quick_start/img/stm32_8.png and /dev/null differ diff --git a/docs/source/quick_start/migration.rst b/docs/source/quick_start/migration.rst deleted file mode 100644 index 10f2ef7e..00000000 --- a/docs/source/quick_start/migration.rst +++ /dev/null @@ -1,63 +0,0 @@ -部分改动迁移指南 -======================== - - -usbh_initialize ------------------- - -usbh_initialize 从 v1.6.0 开始新增 event_handler 参数,通常不需要使用,可以传入 NULL。 - -dwc2 glue st ----------------- - -dwc2 从 v1.5.0 开始 glue 文件内置底层初始化,比如 `usb_dc_low_level_init`,底层依赖 `HAL_PCD_MspInit` 和 `HAL_HCD_MspInit`,必须使用 stm32cubemx 生成。第三方平台不保证有这些函数实现,自行检查。 - - -dwc2 glue ----------------- - -dwc2 从 v1.5.1 开始新增 `struct dwc2_user_params`,用于实现多 dwc2 port 不同配置。并替代 `usbd_get_dwc2_gccfg_conf` 和 `usbh_get_dwc2_hccfg_conf` 函数, -并增加 `dwc2_get_user_params` 函数实现,举例如下: - -.. code-block:: C - - #ifndef CONFIG_USB_DWC2_CUSTOM_PARAM - void dwc2_get_user_params(uint32_t reg_base, struct dwc2_user_params *params) - { - memcpy(params, ¶m_common, sizeof(struct dwc2_user_params)); - #ifdef CONFIG_USB_DWC2_CUSTOM_FIFO - struct usb_dwc2_user_fifo_config s_dwc2_fifo_config; - - dwc2_get_user_fifo_config(reg_base, &s_dwc2_fifo_config); - - params->device_rx_fifo_size = s_dwc2_fifo_config.device_rx_fifo_size; - for (uint8_t i = 0; i < MAX_EPS_CHANNELS; i++) { - params->device_tx_fifo_size[i] = s_dwc2_fifo_config.device_tx_fifo_size[i]; - } - #endif - } - #endif - -host serial ----------------- - -从 v1.6.0 开始,主机增加 host serial 框架,用于统一所有类串口设备。以下 API 需要使用新 serial API 替换: - -.. code-block:: C - - int usbh_xxx_set_line_coding(struct usbh_xxx *xxx_class, struct cdc_line_coding *line_coding); - int usbh_xxx_get_line_coding(struct usbh_xxx *xxx_class, struct cdc_line_coding *line_coding); - int usbh_xxx_set_line_state(struct usbh_xxx *xxx_class, bool dtr, bool rts); - - int usbh_xxx_bulk_in_transfer(struct usbh_xxx *xxx_class, uint8_t *buffer, uint32_t buflen, uint32_t timeout); - int usbh_xxx_bulk_out_transfer(struct usbh_xxx *xxx_class, uint8_t *buffer, uint32_t buflen, uint32_t timeout); - -替换为: - -.. code-block:: C - - struct usbh_serial *usbh_serial_open(const char *devname, uint32_t open_flags); - int usbh_serial_close(struct usbh_serial *serial); - int usbh_serial_control(struct usbh_serial *serial, int cmd, void *arg); - int usbh_serial_write(struct usbh_serial *serial, const void *buffer, uint32_t buflen); - int usbh_serial_read(struct usbh_serial *serial, void *buffer, uint32_t buflen); diff --git a/docs/source/quick_start/opensource.rst b/docs/source/quick_start/opensource.rst deleted file mode 100644 index 7990538e..00000000 --- a/docs/source/quick_start/opensource.rst +++ /dev/null @@ -1,62 +0,0 @@ -官方开源项目分享 -==================== - -除了基本的厂家 SDK 支持以外,我们还对一些火热的开源项目进行了支持,以便于开发者更好的使用这些项目。下面列举适配的 demo 工程链接,具体适配层参考 https://github.com/cherry-embedded/CherryUSB/tree/master/platform 。 - -DAPLINK --------------- - -适配链接:https://github.com/cherry-embedded/CherryDAP - -Blackmagic --------------- - -适配链接:https://github.com/zhangjiance/bmp-hpm-port - -RT-Thread --------------- - -适配链接:https://github.com/RT-Thread/rt-thread - -NUTTX/VELA --------------- - -适配链接:https://github.com/CherryUSB/cherryusb_nuttx - -Zephyr --------------- - -适配链接:https://github.com/hpmicro/zephyr_sdk_glue - -Cangaroo --------------- - -Cangaroo is an open source can bus analyzer software. We provide four-channel CANFD analyzer based on hpmicro hpm5361 - -适配上位机链接:https://github.com/RCSN/cangaroo_hpmicro_canfd_analyzer -适配下位机链接:https://github.com/RCSN/hpm_sdk_extra/tree/main/demos/cangaroo_hpmicro - -LVGL --------------- - -适配链接:https://github.com/cherry-embedded/CherryUSB/tree/master/platform/lvgl - -QMK --------------- - -QMK is an open-source keyboard firmware for Atmel AVR and Arm USB families. - -适配链接:待开放 - -Klipper --------------- - -Klipper is a 3d-printer firmware. - -适配链接:待开放 - - -MAKCU/KMBOX --------------- - -懂的都懂,不开放 \ No newline at end of file diff --git a/docs/source/quick_start/q&a.rst b/docs/source/quick_start/q&a.rst deleted file mode 100644 index 391b7037..00000000 --- a/docs/source/quick_start/q&a.rst +++ /dev/null @@ -1,137 +0,0 @@ -Q & A -============================== - -移植提问模板 ----------------- - -请在下列途径提交问题: -- RT-Thread 官方论坛: https://club.rt-thread.org/ask/tag/5f5f851966917b14.html -- Github issue: https://github.com/cherry-embedded/CherryUSB/issues/new/choose - -提问中请包含以下信息: - -- 使用的版本 -- 使用的板子,引脚,USB IP -- 是否配置 USB 中断,USB 时钟,USB 引脚,USB phy 配置,以及 USB 寄存器地址是否正确,截图 -- 是否能进 USB 中断 -- 芯片是否带有 cache功能,是否做了 no cache 处理,截图 -- USB 电路是否画正确,是否使用杜邦线连接,是否直连,如果正常,请说明正常原因 -- 如果能进中断,配置 **#define CONFIG_USB_DBG_LEVEL USB_DBG_LOG** 并提供 log,仅限商业 IP, 其余 IP 禁止开启 log,否则无法枚举 -- 是否流片并销售 - -其余问题提问模板 ------------------- - -具体说明现象,复现方式,使用我提供的 demo 再测试,以及提供完整 log - -CherryUSB 性能能到多少 ----------------------------------------------------------------- - -参考 :ref:`performace_show` - -ST IP 命名问题 ------------------- - -ST 命名为 USB_OTG_FS, USB_OTG_HS,并不是说明本身是高速或者全速,只是代表可以支持到高速,但是本身都是全速,需要外挂高速phy。因此,提问禁止说这两个词,请使用 USB0(PA11/PA12),USB1(PB14/PB15) 代替。其余国产厂家同理。 - -GD IP 问题 ------------------- - -GD IP 采用 DWC2,但是读取的硬件参数都是 0(我也不懂为什么不给人知道),因此需要用户自行知道硬件信息,从 1.5.0 开始由于需要读取硬件信息,因此无法直接使用。 - -其次 GD 复位以后无法使用 EPDIS 功能关闭端点,需要用户删除 reset 中断中的以下代码: - -.. code-block:: C - - USB_OTG_INEP(i)->DIEPCTL = (USB_OTG_DIEPCTL_EPDIS | USB_OTG_DIEPCTL_SNAK); - USB_OTG_OUTEP(i)->DOEPCTL = (USB_OTG_DOEPCTL_EPDIS | USB_OTG_DOEPCTL_SNAK); - -除此之外可能存在其他未知 BUG,请自行测试。 - -开启 USB_LOG_DBG 后无法枚举 ----------------------------------------------------------------- - -有且仅有商业性 IP 开启后可以枚举,其余 IP 禁止开启,否则无法枚举。懂得都懂。 - -USB3 CV测试用哪个版本 ------------------------------- - -1.4.3 版本及以上 - -Ep addr XXX fifo overflow ------------------------------- - -.. figure:: img/question1.png - -该错误表示该端点默认设置的 fifo 空间不够用,需要增大 fifo 空间,通常见于 DWC2/MUSB IP。FIFO 设置参考相关的 glue 文件。 - -Ep addr XXX overflow ------------------------------- - -.. figure:: img/question2.png - -该错误表示该 IP 硬件上没有这么多端点, 请更换 IP or 减少端点使用。 -当然也可以修改为双向端点,考虑到不是所有的 IP 都支持双向端点,因此默认 demo 不做双向功能,举例默认是 81 02 这样的而不是 81 01,如果支持,自行修改。某些 IP 双向端点可能会占用相同的硬件信息,不一定能同时使用,自行检查。 - -This dwc2 version does not support dma mode, so stop working ----------------------------------------------------------------- - -该 DWC2 版本不支持 dma 模式,禁止使用。不使用 DMA 模式会频繁触发 NAK 中断(大概几十us一次),CPU 占用率过高。 - -OTG 有哪些芯片支持 ------------------------------- - -当前主线仅 HPM 芯片支持 OTG 功能,通过 ID 引脚自动切换主从模式,其他芯片请使用手动切换模式 OR 自行实现添加 ID 识别的驱动。 - -PC 识别的 COM 口如何更改名称 ----------------------------------------------------------------- - -这是微软对 CDC ACM 的驱动问题,无法修改,如需修改,请联系微软并缴纳费用+编写驱动后即可更改。 - -connect 和 disconnect event 不触发 ----------------------------------------------------------------- - -当前仅 hpm 芯片支持 connect 和 disconnect 事件,其他芯片请使用 USB 检测 vbus 电路。DWC2 IP 支持,但是由于需要占用引脚,并且大多是log 口,然后不同使能的配置也不一样,因此不做支持。 - -__has_include 报错 ------------------------------------------------------------------- -如果报错,需要编译器支持 c99 语法,如果是 keil,请用 ac6 编译器 - -CONFIG_USB_HS 何时使用 ----------------------------------------------------------------- - -当你的芯片硬件支持高速,并想初始化成高速模式时开启,相关 IP 会根据该宏配置内部或者外部 高速 PHY。 - -Failed to enable port ----------------------------------------------------------------- - -供电不足或者硬件 USB 电路问题 - -移植 usb host 出现 urb 返回 -12/-14 ----------------------------------------------------------------- - -检查 phy 配置,cache 配置(如果有),电源供电(建议自供电) - -USB_ERR_NAK 说明 ----------------------------------------------------------------- - -USB_ERR_NAK 只存在于 DWC2 buffer dma/slave 模式(我们不使用 slave 模式),DWC2 在 buffer dma模式下对于中断传输不支持硬件处理 NAK 中断,因此需要软件处理,导致 NAK 中断非常多,建议搭配定时器使用。 -DWC2 scatter/gather dma 模式下全部由硬件处理,但是不支持 split 传输。总结, **食之无味,弃之可惜**。 - -USB host 连接 USB 网卡问题 ----------------------------------------------------------------- - -表现为能识别网卡并且分配到 IP 地址,但是无法 ping 通,这是因为网卡自身需要开启自动拨号,通常需要使用 AT 口设置。具体为 EC20/ML307 等模块。 - - -什么时候需要开启 CONFIG_USB_DCACHE_ENABLE -------------------------------------------------- - -当芯片带有 cache 功能,并且没有使用 no cache ram 时需要开启此宏以保证数据一致性。 **使用 EHCI 时,内部依旧需要使用 nocache ram**。通常,对于第三方平台或者组件,没有使用 no cache ram 宏修饰,都是使用全局变量或者 malloc 等 -操作,这部分 RAM 通常是走 cache 的,因此需要开启此宏。建议第三方平台使用时,必须开启。 - -哪些 IP 对数据有对齐要求 -------------------------------------------------- - -- 在未开启 CONFIG_USB_DCACHE_ENABLE 时,仅 DWC2/WCH/AIC IP 需要 4字节对齐,其余 1字节对齐即可。 -- 在开启 CONFIG_USB_DCACHE_ENABLE 时,所有 IP 都需要对齐到 CONFIG_USB_ALIGN_SIZE 字节 \ No newline at end of file diff --git a/docs/source/quick_start/rtthread.rst b/docs/source/quick_start/rtthread.rst deleted file mode 100644 index 132015d9..00000000 --- a/docs/source/quick_start/rtthread.rst +++ /dev/null @@ -1,62 +0,0 @@ -基于 RT-Thread 软件包开发指南 -=============================== - -.. note:: CherryUSB 已经加入 RT-Thread 主线,可以选择使用主线版本,配置方式相同。 - -本节主要介绍使用 RT-Thread 提供的软件包管理器来配置工程,以 env 作为演示。本节操作不同芯片都一样,后续不再重复讲解。打开 env 以后使用 menuconfig 进入包管理器,并在如图所示路径中选择 CherryUSB。 - -.. figure:: img/env0.png - -从机配置 --------------------------- - -* 选择 Enable usb device mode 并敲回车进入。 -* 首先第一个配置是配置 USB 的速度,分为 **FS、HS**,表示使用全速还是高速功能。高速功能要求内置高速 PHY 或者外接 PHY -* 其次第二个配置则是选择 USB device ip,不清楚自己芯片是哪个 ip 的可以参考 **port** 目录下对应的 readme。 -* 选择你想使用的 class -* 选择是否使用 demo 模板 - -.. figure:: img/env1.png - -* 最后退出保存即可。 -* 拷贝 `cherryusb_config_template.h` 文件到自己工程目录下,命名为 `usb_config.h`,并添加相应的目录头文件路径,并修改以下内容: - -.. code-block:: C - - #include "rtthread.h" - - #define CONFIG_USB_PRINTF(...) rt_kprintf(__VA_ARGS__) - -* USB IP 相关的 config 需要用户自己根据芯片实际情况修改 -* 在代码中实现 `usb_dc_low_level_init` 函数 -* 在 USB 中断函数中调用 `USBD_IRQHandler`,并传入 `busid` -* 调用 `usbd_initialize` 并填入 `busid` 和 USB IP 的 `reg base`, `busid` 从 0 开始,不能超过 `CONFIG_USBDEV_MAX_BUS` -* 使用 `scons --target=mdk5` 或者 `scons` 进行编译,如果是mdk,需要使用 AC6 编译器 -* 如果芯片带 cache,cache 修改参考 :ref:`usb_cache` 章节 - -主机配置 --------------------------- - -* 选择 Enable usb host mode 并敲回车进入 -* 选择 USB host ip,不清楚自己芯片是哪个 ip 的可以参考 **port** 目录下对应的 readme -* 根据需要勾选 class 驱动 -* 选择是否开启模板 demo,推荐不用 - -.. figure:: img/env2.png - -* 最后退出保存即可。 -* 拷贝 `cherryusb_config_template.h` 文件到自己工程目录下,命名为 `usb_config.h`,并添加相应的目录头文件路径,并实现以下内容: - -.. code-block:: C - - #include "rtthread.h" - - #define CONFIG_USB_PRINTF(...) rt_kprintf(__VA_ARGS__) - -* USB IP 相关的 config 需要用户自己根据芯片实际情况修改 -* 在代码中实现 `usb_hc_low_level_init` 函数 -* 在 USB 中断函数中调用 `USBH_IRQHandler`,并传入 `busid` -* 调用 `usbh_initialize` 并填入 `busid` 和 USB IP 的 `reg base` 还有 `event_handler` 可缺省为NULL, `busid` 从 0 开始,不能超过 `CONFIG_USBHOST_MAX_BUS` -* 使用 `scons --target=mdk5` 或者 `scons` 进行编译,如果是mdk,需要使用 AC6 编译器 -* 链接脚本修改参考 :ref:`usbh_link_script` 章节 -* 如果芯片带 cache,cache 修改参考 :ref:`usb_cache` 章节 diff --git a/docs/source/quick_start/share.rst b/docs/source/quick_start/share.rst deleted file mode 100644 index a57a8e1e..00000000 --- a/docs/source/quick_start/share.rst +++ /dev/null @@ -1,27 +0,0 @@ -开发者经验/开源项目分享 -======================== - -- `RT-Thread-CherryUSB - RT-Thread `_ - -- `[HPM-DIY]hpm6750 USB开源协议栈性能对比-cherryusb or tinyusb? `_ - -- `RT-Thread-CherryUSB移植笔记(一):APM32F407VGT6 DWC2移植 Port.A Full-Speed + Por.B High-SpeedRT-Thread问答社区 - RT-Thread `_ - -- `华大HC32F460XXX移植cherryusb协议栈,实现USB CDC ACM_cherryusb移植教程-CSDN博客 `_ - -- `rt-thread使用cherryusb实现虚拟串口-CSDN博客 `_ - -- `F1C100S+rtt+CherryUSB的USB HOST成功读到U盘 / 全志 SOC / WhyCan Forum(哇酷开发者社区) `_ - -- `模仿stm32标准库风格写的库文件(f1c100s/f1c200s),且已移植了rt-thread、lvgl、fatfs、cherryusb / 全志 SOC / WhyCan Forum(哇酷开发者社区) `_ - -- `printalyzer-timer: F-Stop enlarging timer and print exposure meter `_ - -- `MiSTeryNano: Atari STE MiSTery core for the Tang Nano 20k FPGA `_ - -- `Cherryuf2 `_ - -- `PicoPiFi: Driverless RNDIS USB WIFI Dongle `_ - -- `phobia: Phobia Motor Controller `_ - diff --git a/docs/source/quick_start/start.rst b/docs/source/quick_start/start.rst deleted file mode 100644 index c6223b61..00000000 --- a/docs/source/quick_start/start.rst +++ /dev/null @@ -1,53 +0,0 @@ -入门必看 -================== - -首先欢迎大家来到 usb 的世界,在这里你可以学习到 usb 各种知识以及 cherryusb 的移植使用进阶等等。但是呢,刚进来的你,一定很懵懂,因为 USB 很难(其实当你学会了 cherryusb以后,你会发现,USB 一点都不难), -那么这种情况下,你的学习路线,应该是怎么样呢?在这里,我推荐大家是按照我得学习路线来学习,这样对你的 USB 成长是最有帮助的,并且你也不会中途放弃。 - -首先,不允许上来就看概念,有句古诗说的好, **纸上得来终觉浅,绝知此事要躬行** ,光看纸面上的东西,你是学不到什么的,只有当自己实践了,你才能更深入的了解这些概念。那么作为初学者,你应该怎么做呢?请看以下步骤。 - - -第一步 -------------- - -你需要学过 C 语言,UART, DMA,这是基础,如果没学过,请去学习,不然你会很吃力。你会问 USB 跟 UART/DMA 有什么关系? 我只能说两个字, **等价** - -第二步 -------------- - -下载 demo 工程并跑通能运行, **建议学习慢的,使用 demo 同型号芯片**,学习快的,可以选择自己移植相关支持的型号的芯片。你连 demo 都跑不通,你学什么 USB,你说对不对? - -第三步 ---------- - -非常好,到这步,说明你已经能熟练移植和跑通所有示例了,那么接下来,你应该学习什么呢? **事务**, **请求** 和 **描述符** (在 USB 的学习过程中,你只需要知道这三个,其余都不需要知道)。 - -第四步 ----------- - -首先我们需要知道 USB 事务包含 SETUP/IN/OUT,其实就是等价于发送命令,发送数据和接收数据,很简单。至于下面枚举中你在外面的网络中所听到的控制阶段,数据阶段,状态阶段,他不是事务,他只是用多个事务代表了一个阶段而已。 - -第五步 ----------- - -然后你再去看 **USB 枚举** 章节并且知道了一个概念: **描述符** ,这个时候,你就可以去简单看看什么是描述符,有哪些描述符,然后你需要记住, **设备、配置、接口、端点描述符的组成**,并背下来,其余的你都不需要知道,因为其他都是固定的,后续都是 CV 。群文件有各类设备枚举的抓包,可以下下来看看。 - -第六步 ----------- - -然后呢,你可以再去看看什么是 **请求** ,请求结构体的组成,看看有哪些请求,简单了解即可,为什么呢?因为它不过就是 8 字节的数据格式,大家都会写一个 UART + 自定义协议,那么 USB 的请求也是一样的,只不过是规定好了而已。 - -第七步 ----------- - -这个时候,你该去熟悉下协议栈的一些 API 了,参考 **API 手册** 章节。并且你需要知道中断完成的条件是什么,什么时候算接收完成,什么时候算发送完成,可以参考 **USB 知识点拓展** 章节。 - -第八步 ----------- - -到这步呢,你肯定已经非常懂了,然后就可以开始你的一些小功能小项目了,在此期间呢,请循环查看 **USB 知识点拓展** 章节,直到你真的理解了,因为这些内容是非常重要的,会影响我们代码的执行结果。 - -第九步 ----------- - -都到这步了,你应该不需要我了,这个时候,你可以去看看 USB 概念,看看 USB 的一些细节,看看 CherryUSB 的代码流程了。然后就是巩固巩固再巩固了。恭喜你,出师了!!! diff --git a/docs/source/quick_start/transplant.rst b/docs/source/quick_start/transplant.rst deleted file mode 100644 index 710497d4..00000000 --- a/docs/source/quick_start/transplant.rst +++ /dev/null @@ -1,137 +0,0 @@ -芯片通用移植指南 -========================= - -本节主要介绍所有带 USB IP 的芯片,移植 CherryUSB 主从协议栈时的通用步骤和注意事项。在移植之前,需要 **你准备好一个可以打印 helloworld 的基本工程** ,默认打印使用 `printf`, 如果是主机模式, **则需要准备好可以正常执行 os 调度的基本工程**。 - -USB Device 移植要点 ------------------------ - -- 拷贝 CherryUSB 源码到工程目录下,并按需添加源文件和头文件路径,头文件路径建议全部添加。其中 `usbd_core.c` 和 `usb_dc_xxx.c` 为必须添加项。而 `usb_dc_xxx.c` 是芯片所对应的 USB IP dcd 部分驱动,如果不知道自己芯片属于那个 USB IP,参考 **port** 目录下的不同 USB IP 的 readme。如果使用的 USB IP 没有支持,只能自己实现了 -- 拷贝 `cherryusb_config_template.h` 文件到自己工程目录下,命名为 `usb_config.h`,并添加相应的目录头文件路径 -- 实现 `usb_dc_low_level_init` 函数(该函数主要负责 USB 时钟、引脚、中断的初始化)。该函数可以放在你想要放的任何参与编译的 c 文件中。如何进行 USB 的时钟、引脚、中断等初始化,请自行根据你使用的芯片原厂提供的源码中进行添加。 -- 在中断函数中调用 `USBD_IRQHandler`,并传入 `busid`, 如果你的 SDK 中中断入口已经存在 `USBD_IRQHandler` ,请更改 USB 协议栈中的名称 -- 如果芯片带 cache,cache 修改参考 :ref:`usb_cache` 章节 -- 注册描述符并调用 `usbd_initialize`,填入 `busid` 和 USB IP 的 `reg base`, `busid` 从 0 开始,不能超过 `CONFIG_USBDEV_MAX_BUS`,可以直接使用 demo 下的 template - -USB Host 移植要点 ------------------------ - -- 拷贝 CherryUSB 源码到工程目录下,并按需添加源文件和头文件路径,头文件路径建议全部添加。其中 `usbh_core.c` 、 `usb_hc_xxx.c` 以及 **osal** 目录下源文件(根据不同的 os 选择对应的源文件)为必须添加项。而 `usb_hc_xxx.c` 是芯片所对应的 USB IP hcd 部分驱动,如果不知道自己芯片属于那个 USB IP,参考 **port** 目录下的不同 USB IP 的 readme。如果使用的 USB IP 没有支持,只能自己实现了 -- 拷贝 `cherryusb_config_template.h` 文件到自己工程目录下,命名为 `usb_config.h`,并添加相应的目录头文件路径 -- 实现 `usb_hc_low_level_init` 函数(该函数主要负责 USB 时钟、引脚、中断的初始化)。该函数可以放在你想要放的任何参与编译的 c 文件中。如何进行 USB 的时钟、引脚、中断等初始化,请自行根据你使用的芯片原厂提供的源码中进行添加。 -- 调用 `usbh_initialize` 并填入 `busid` 和 USB IP 的 `reg base` 还有 `event_handler` 可缺省为NULL, `busid` 从 0 开始,不能超过 `CONFIG_USBHOST_MAX_BUS` -- 在中断函数中调用 `USBH_IRQHandler`,并传入 `busid`, 如果你的 SDK 中中断入口已经存在 `USBH_IRQHandler` ,请更改 USB 协议栈中的名称 -- 链接脚本修改参考 :ref:`usbh_link_script` 章节 -- 如果芯片带 cache,cache 修改参考 :ref:`usb_cache` 章节 -- 调用 `usbh_initialize` ,填入 `busid` 和 USB IP 的 `reg base` 还有 `event_handler` 可缺省为NULL, `busid` 从 0 开始,不能超过 `CONFIG_USBHOST_MAX_BUS` 。基础的 cdc + hid + msc 参考 `usb_host.c` 文件,其余参考 **platform** 目录下适配 - -.. _usbh_link_script: - -主机链接脚本修改 ------------------------ - -在使用主机时,如果没有修改链接脚本,会报 `__usbh_class_info_start__` 和 `__usbh_class_info_end__` 未定义的错误。因为主机协议栈需要在链接脚本中添加一个 section 来存储 class 信息。 - -- 如果使用的是 KEIL 无需修改 - -- 如果使用的是 GCC ,需要在链接脚本中添加如下代码(需要放在 flash 位置,建议放最后): - -.. code-block:: C - - // 在 ld 文件中添加如下代码 - . = ALIGN(4); - __usbh_class_info_start__ = .; - KEEP(*(.usbh_class_info)) - __usbh_class_info_end__ = .; - -GCC 举例如下: - -.. code-block:: C - - /* The program code and other data into "FLASH" Rom type memory */ - .text : - { - . = ALIGN(4); - *(.text) /* .text sections (code) */ - *(.text*) /* .text* sections (code) */ - *(.glue_7) /* glue arm to thumb code */ - *(.glue_7t) /* glue thumb to arm code */ - *(.eh_frame) - - KEEP (*(.init)) - KEEP (*(.fini)) - . = ALIGN(4); - __usbh_class_info_start__ = .; - KEEP(*(.usbh_class_info)) - __usbh_class_info_end__ = .; - . = ALIGN(4); - _etext = .; /* define a global symbols at end of code */ - } > FLASH - -- Segger Embedded Studio 举例如下: - -.. code-block:: C - - define block cherryusb_usbh_class_info { section .usbh_class_info }; - - define exported symbol __usbh_class_info_start__ = start of block cherryusb_usbh_class_info; - define exported symbol __usbh_class_info_end__ = end of block cherryusb_usbh_class_info + 1; - - place in AXI_SRAM { block cherryusb_usbh_class_info }; - keep { section .usbh_class_info}; - - -.. _usb_cache: - -cache 配置修改 -------------------------------- - -对于带 cache 的芯片,协议栈以及 port 中不会对 cache 区域的 ram 进行 clean 或者 invalid,所以需要使用一块非 cache 区域的 ram 来维护。 -`USB_NOCACHE_RAM_SECTION` 宏表示将变量指定到非 cache ram上,默认 `USB_NOCACHE_RAM_SECTION` 定义为 `__attribute__((section(".noncacheable")))`。 -因此,用户需要在对应的链接脚本中添加 no cache ram 的 section,并且 section 段包含 `.noncacheable`。 - -.. note:: 需要注意,光修改链接脚本中的 nocache section 是不够的,还需要配置该 section 中的 ram 是真的 nocache,一般需要配置 mpu 属性(arm 的参考 stm32h7 demo)。 - -GCC: - -.. code-block:: C - - MEMORY - { - RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 256K - 64K - RAM_nocache (xrw) : ORIGIN = 0x20030000, LENGTH = 64K - FLASH (rx) : ORIGIN = 0x8000000, LENGTH = 512K - } - - ._nocache_ram : - { - . = ALIGN(4); - *(.noncacheable) - } >RAM_nocache - - -SCT: - -.. code-block:: C - - LR_IROM1 0x08000000 0x00200000 { ; load region size_region - ER_IROM1 0x08000000 0x00200000 { ; load address = execution address - *.o (RESET, +First) - *(InRoot$$Sections) - .ANY (+RO) - .ANY (+XO) - } - RW_IRAM2 0x24000000 0x00070000 { ; RW data - .ANY (+RW +ZI) - } - USB_NOCACHERAM 0x24070000 0x00010000 { ; RW data - *(.noncacheable) - } - } - -ICF: - -.. code-block:: C - - define region NONCACHEABLE_RAM = [from 0x1140000 size 256K]; - place in NONCACHEABLE_RAM { section .noncacheable, section .noncacheable.init, section .noncacheable.bss }; // Noncacheable diff --git a/docs/source/show/img/usbdev_msc.png b/docs/source/show/img/usbdev_msc.png deleted file mode 100644 index 30f22383..00000000 Binary files a/docs/source/show/img/usbdev_msc.png and /dev/null differ diff --git a/docs/source/show/img/usbdev_rndis_linux.png b/docs/source/show/img/usbdev_rndis_linux.png deleted file mode 100644 index 94b97312..00000000 Binary files a/docs/source/show/img/usbdev_rndis_linux.png and /dev/null differ diff --git a/docs/source/show/img/usbdev_rndis_lwip.png b/docs/source/show/img/usbdev_rndis_lwip.png deleted file mode 100644 index f4cfd0b3..00000000 Binary files a/docs/source/show/img/usbdev_rndis_lwip.png and /dev/null differ diff --git a/docs/source/show/img/usbdev_rndis_lwip2.png b/docs/source/show/img/usbdev_rndis_lwip2.png deleted file mode 100644 index 3fde91f9..00000000 Binary files a/docs/source/show/img/usbdev_rndis_lwip2.png and /dev/null differ diff --git a/docs/source/show/img/usbdev_rndis_wifi.png b/docs/source/show/img/usbdev_rndis_wifi.png deleted file mode 100644 index d6817876..00000000 Binary files a/docs/source/show/img/usbdev_rndis_wifi.png and /dev/null differ diff --git a/docs/source/show/img/usbdev_rndis_wifi2.png b/docs/source/show/img/usbdev_rndis_wifi2.png deleted file mode 100644 index dba9f3dd..00000000 Binary files a/docs/source/show/img/usbdev_rndis_wifi2.png and /dev/null differ diff --git a/docs/source/show/img/usbdev_rndis_win.png b/docs/source/show/img/usbdev_rndis_win.png deleted file mode 100644 index 5293023a..00000000 Binary files a/docs/source/show/img/usbdev_rndis_win.png and /dev/null differ diff --git a/docs/source/show/img/usbdev_uvc_mjpeg.png b/docs/source/show/img/usbdev_uvc_mjpeg.png deleted file mode 100644 index a2321c15..00000000 Binary files a/docs/source/show/img/usbdev_uvc_mjpeg.png and /dev/null differ diff --git a/docs/source/show/img/usbdev_uvc_yuv.png b/docs/source/show/img/usbdev_uvc_yuv.png deleted file mode 100644 index a630cd67..00000000 Binary files a/docs/source/show/img/usbdev_uvc_yuv.png and /dev/null differ diff --git a/docs/source/show/img/usbhost_ax88772_1.png b/docs/source/show/img/usbhost_ax88772_1.png deleted file mode 100644 index a267b292..00000000 Binary files a/docs/source/show/img/usbhost_ax88772_1.png and /dev/null differ diff --git a/docs/source/show/img/usbhost_ax88772_2.png b/docs/source/show/img/usbhost_ax88772_2.png deleted file mode 100644 index fc6e96fc..00000000 Binary files a/docs/source/show/img/usbhost_ax88772_2.png and /dev/null differ diff --git a/docs/source/show/img/usbhost_hub.png b/docs/source/show/img/usbhost_hub.png deleted file mode 100644 index 011468c7..00000000 Binary files a/docs/source/show/img/usbhost_hub.png and /dev/null differ diff --git a/docs/source/show/img/usbhost_hub2.png b/docs/source/show/img/usbhost_hub2.png deleted file mode 100644 index 00c09d6f..00000000 Binary files a/docs/source/show/img/usbhost_hub2.png and /dev/null differ diff --git a/docs/source/show/img/usbhost_msc.png b/docs/source/show/img/usbhost_msc.png deleted file mode 100644 index ec546a8d..00000000 Binary files a/docs/source/show/img/usbhost_msc.png and /dev/null differ diff --git a/docs/source/show/img/usbhost_msc_xhci.png b/docs/source/show/img/usbhost_msc_xhci.png deleted file mode 100644 index 084250f2..00000000 Binary files a/docs/source/show/img/usbhost_msc_xhci.png and /dev/null differ diff --git a/docs/source/show/img/usbhost_rndis.png b/docs/source/show/img/usbhost_rndis.png deleted file mode 100644 index 12ab1a4e..00000000 Binary files a/docs/source/show/img/usbhost_rndis.png and /dev/null differ diff --git a/docs/source/show/img/usbhost_uvc.gif b/docs/source/show/img/usbhost_uvc.gif deleted file mode 100644 index c4df04e0..00000000 Binary files a/docs/source/show/img/usbhost_uvc.gif and /dev/null differ diff --git a/docs/source/show/img/usbhost_wifi.png b/docs/source/show/img/usbhost_wifi.png deleted file mode 100644 index e57fd85b..00000000 Binary files a/docs/source/show/img/usbhost_wifi.png and /dev/null differ diff --git a/docs/source/show/index.rst b/docs/source/show/index.rst deleted file mode 100644 index c5d3f708..00000000 --- a/docs/source/show/index.rst +++ /dev/null @@ -1,103 +0,0 @@ -.. _performace_show: - -性能展示 -============================== - -以下演示了 CherryUSB 在不同应用中的性能表现。主要演示高速模式,全速看不出什么性能差异。 - -CDC ACM 通信 ----------------- - -可以达到硬件极限性能,当然需要硬件理论支持到这速度,CherryUSB 就支持到这速度,举例如下: - -- HPM 系列(从机可以到 42MB/S, 主机 44MB/S, 已经达到硬件极限) -- BL 系列(从机 32MB/S, 主机 25MB/S, 已经达到硬件极限) -- STM32F4 全速(从机 900KB/S, 主机 1.12MB/S, 已经达到硬件极限) - -从机测速demo: cdc_acm_template.c 并且关闭 log,脚本使用 `tools/test_srcipts/test_cdc_speed.py` -主机测速demo: usb_host.c 中 TEST_USBH_CDC_SPEED=1 - -USB Device MSC ------------------ - -演示 USB Device MSC 使用 SDXC3.0 + EMMC 测试。 - -.. figure:: img/usbdev_msc.png - -USB Device RNDIS ------------------------ - -.. note:: 默认 rndis 仅支持单包,因此下面速度为最低速度。多包支持需要联系作者。 - -演示 USB Device RNDIS 局域网下搭配 lwip 的速度。 - -作为 client - -.. figure:: img/usbdev_rndis_lwip.png - -作为 server - -.. figure:: img/usbdev_rndis_lwip2.png - -演示 USB Device RNDIS + WIFI 透传测试。 - -.. figure:: img/usbdev_rndis_wifi.png -.. figure:: img/usbdev_rndis_wifi2.png - -演示 USB Device RNDIS + 百兆以太网透传测试。 - -.. figure:: img/usbdev_rndis_win.png -.. figure:: img/usbdev_rndis_linux.png - -USB Device UVC ------------------------ - -演示 USB Device UVC + 摄像头传输 YUYV/MJPEG 640 * 480 图像。FPS 30。 - -.. figure:: img/usbdev_uvc_mjpeg.png -.. figure:: img/usbdev_uvc_yuv.png - -USB Host HUB ------------------------ - -多级 hub 支持,演示 1托 7 HUB - -.. figure:: img/usbhost_hub.png -.. figure:: img/usbhost_hub2.png - -USB Host MSC ------------------------ - -演示 USB Host MSC 在 USB2.0 和 USB3.0 下的速度,U盘推荐使用固态测试。 - -.. figure:: img/usbhost_msc.png -.. figure:: img/usbhost_msc_xhci.png - -USB Host UVC ------------------------ - -演示 USB Host UVC 驱动 648 * 480 YUV 摄像头。FPS 30。 - -.. figure:: img/usbhost_uvc.gif - -USB Host ASIX 网卡 ------------------------ - -演示 USB Host 驱动 AX88772 USB 以太网模块。 - -.. figure:: img/usbhost_ax88772_1.png -.. figure:: img/usbhost_ax88772_2.png - -USB Host RNDIS 网卡 ------------------------ - -演示 USB Host 驱动手机,手机开启 USB 共享网络即可使用 RNDIS 。 - -.. figure:: img/usbhost_rndis.png - -USB Host WIFI ------------------------ - -演示 USB Host 驱动 BL616 USB WIFI。 - -.. figure:: img/usbhost_wifi.png diff --git a/docs/source/support/img/dwc2_hostuac.png b/docs/source/support/img/dwc2_hostuac.png deleted file mode 100644 index 6050f531..00000000 Binary files a/docs/source/support/img/dwc2_hostuac.png and /dev/null differ diff --git a/docs/source/support/img/dwc2_hostuvc1.png b/docs/source/support/img/dwc2_hostuvc1.png deleted file mode 100644 index 70b4dd1a..00000000 Binary files a/docs/source/support/img/dwc2_hostuvc1.png and /dev/null differ diff --git a/docs/source/support/img/dwc2_hostuvc2.png b/docs/source/support/img/dwc2_hostuvc2.png deleted file mode 100644 index 8885e90e..00000000 Binary files a/docs/source/support/img/dwc2_hostuvc2.png and /dev/null differ diff --git a/docs/source/support/img/dwc2_hostuvc3.png b/docs/source/support/img/dwc2_hostuvc3.png deleted file mode 100644 index fb3e1eef..00000000 Binary files a/docs/source/support/img/dwc2_hostuvc3.png and /dev/null differ diff --git a/docs/source/support/img/ehci_hostuvc1.png b/docs/source/support/img/ehci_hostuvc1.png deleted file mode 100644 index 2bd6590a..00000000 Binary files a/docs/source/support/img/ehci_hostuvc1.png and /dev/null differ diff --git a/docs/source/support/img/ehci_hostuvc2.png b/docs/source/support/img/ehci_hostuvc2.png deleted file mode 100644 index f44fa68c..00000000 Binary files a/docs/source/support/img/ehci_hostuvc2.png and /dev/null differ diff --git a/docs/source/support/img/mtpdev.png b/docs/source/support/img/mtpdev.png deleted file mode 100644 index 513b8ac9..00000000 Binary files a/docs/source/support/img/mtpdev.png and /dev/null differ diff --git a/docs/source/support/img/ohci.png b/docs/source/support/img/ohci.png deleted file mode 100644 index 171f77be..00000000 Binary files a/docs/source/support/img/ohci.png and /dev/null differ diff --git a/docs/source/support/img/rndisrx.png b/docs/source/support/img/rndisrx.png deleted file mode 100644 index ce1133ed..00000000 Binary files a/docs/source/support/img/rndisrx.png and /dev/null differ diff --git a/docs/source/support/img/rndistx.png b/docs/source/support/img/rndistx.png deleted file mode 100644 index 69e45db8..00000000 Binary files a/docs/source/support/img/rndistx.png and /dev/null differ diff --git a/docs/source/support/img/tmcdev1.png b/docs/source/support/img/tmcdev1.png deleted file mode 100644 index 1eaf7155..00000000 Binary files a/docs/source/support/img/tmcdev1.png and /dev/null differ diff --git a/docs/source/support/img/tmcdev2.png b/docs/source/support/img/tmcdev2.png deleted file mode 100644 index 97c8297b..00000000 Binary files a/docs/source/support/img/tmcdev2.png and /dev/null differ diff --git a/docs/source/support/img/usbhost_uvc.gif b/docs/source/support/img/usbhost_uvc.gif deleted file mode 100644 index c4df04e0..00000000 Binary files a/docs/source/support/img/usbhost_uvc.gif and /dev/null differ diff --git a/docs/source/support/index.rst b/docs/source/support/index.rst deleted file mode 100644 index e30c4bb0..00000000 --- a/docs/source/support/index.rst +++ /dev/null @@ -1,43 +0,0 @@ -商业支持 -============================== - -以下内容为商业收费类,如需支持,请邮件到 1203593632@qq.com。 - -- OHCI 驱动 - -.. figure:: img/ohci.png - -- EHCI IP 中 ISO 驱动和 UAC/UVC 框架,搭配主机 UVC & UAC 类(这部分是开源的)使用。iso 支持一个微帧 1/2/3 包,支持 MJPEG 和 YUV 摄像头 - -.. figure:: img/ehci_hostuvc1.png -.. figure:: img/ehci_hostuvc2.png - -演示 USB Host UVC 驱动 648 * 480 YUV 摄像头。FPS 30。 - -.. figure:: img/usbhost_uvc.gif - -- DWC2 IP 中 ISO 驱动和 UAC/UVC 框架,搭配主机 UVC & UAC 类(这部分是开源的)使用。iso 支持一个微帧 1/2/3 包,支持 MJPEG 和 YUV 摄像头 - -.. figure:: img/dwc2_hostuvc1.png -.. figure:: img/dwc2_hostuvc2.png -.. figure:: img/dwc2_hostuvc3.png -.. figure:: img/dwc2_hostuac.png - -- MUSB IP 中 ISO 驱动和 UAC/UVC 框架,搭配主机 UVC & UAC 类(这部分是开源的)使用。MUSB 需要为 mentor 公司制定的标准 IP - -- 从机 MTP 类驱动, 支持多文件和多文件夹,支持 MCU 端增删文件并与 PC 同步 - -.. figure:: img/mtpdev.png - -- 从机 TMC 类驱动 - -.. figure:: img/tmcdev1.png -.. figure:: img/tmcdev2.png - -- USB 网卡类高性能版本优化,包含 CDC-NCM, CDC-RNDIS, 私有类驱动(支持多包发送和接收),下面举例 RNDIS - -.. figure:: img/rndistx.png -.. figure:: img/rndisrx.png - -- 定制化 class 驱动或者 IP 驱动适配 -- 技术支持相关 \ No newline at end of file diff --git a/docs/source/tools/img/chrytool1.png b/docs/source/tools/img/chrytool1.png deleted file mode 100644 index 8717316a..00000000 Binary files a/docs/source/tools/img/chrytool1.png and /dev/null differ diff --git a/docs/source/tools/img/chrytool2.png b/docs/source/tools/img/chrytool2.png deleted file mode 100644 index a0eb4192..00000000 Binary files a/docs/source/tools/img/chrytool2.png and /dev/null differ diff --git a/docs/source/tools/img/chrytool3.png b/docs/source/tools/img/chrytool3.png deleted file mode 100644 index 52a3556b..00000000 Binary files a/docs/source/tools/img/chrytool3.png and /dev/null differ diff --git a/docs/source/tools/img/chrytool4.png b/docs/source/tools/img/chrytool4.png deleted file mode 100644 index 8ad68400..00000000 Binary files a/docs/source/tools/img/chrytool4.png and /dev/null differ diff --git a/docs/source/tools/img/chrytool5.png b/docs/source/tools/img/chrytool5.png deleted file mode 100644 index 17849324..00000000 Binary files a/docs/source/tools/img/chrytool5.png and /dev/null differ diff --git a/docs/source/tools/img/chrytool6.png b/docs/source/tools/img/chrytool6.png deleted file mode 100644 index 931ccad8..00000000 Binary files a/docs/source/tools/img/chrytool6.png and /dev/null differ diff --git a/docs/source/tools/img/chrytool7.png b/docs/source/tools/img/chrytool7.png deleted file mode 100644 index 283a7fc9..00000000 Binary files a/docs/source/tools/img/chrytool7.png and /dev/null differ diff --git a/docs/source/tools/index.rst b/docs/source/tools/index.rst deleted file mode 100644 index 0ebfb31d..00000000 --- a/docs/source/tools/index.rst +++ /dev/null @@ -1,50 +0,0 @@ -chryusb_configurator --------------------------- - -`chryusb_configurator `_ 主要服务在使用设备协议栈时,生成描述符数组,从而调用 `usbd_desc_register` 进行注册。 - -- 首先我们从 github 下载 chryusb_configurator.exe,然后一路安装就可以了。然后双击打开,点击 `工程`,并点击 `新建工程` - -.. figure:: img/chrytool1.png - -- 新建完成以后,会生成默认的描述符配置,包含 **设备描述符**、 **配置描述符**、 **字符串描述符**,并且 **字符串描述符** 默认支持三个 - -.. figure:: img/chrytool2.png - -- 然后我们可以根据需要修改相关描述符的信息,比如 **设备描述符** 中的 vid、pid,class 参数, **配置描述符** 中的 **Power** 等等 - -- 然后是 class 的添加,需要点击 `文件`,并点击 `新建文件` - -.. figure:: img/chrytool3.png - -- 然后右侧提供了一些 class 的描述符模板,选择一个进行初始化 - -.. figure:: img/chrytool4.png - -- 如果是多个 class ,则上述两步重复操作就可以了 - -- 然后我们根据需要修改相关端点的参数,比如方向、地址、size、interval - -.. figure:: img/chrytool5.png - -- 最后点击 `文件` 并保存文件,后缀为 `.chry` -- 切换到工程文件,后缀是 `.chrybase`, 然后点击 `添加分组配置` 导入刚刚配置好的 class 文件 - -.. figure:: img/chrytool6.png - -- 点击 `工程` 并点击 `保存工程` -- 点击 `编译`,生成描述符数组 - -.. figure:: img/chrytool7.png - -- 复制编译后的文件到自己的工程中使用即可 - - -力科 USB Protocol Suite --------------------------- - -Wireshark --------------------------- - -Audacity --------------------------- diff --git a/docs/source/usb/img/1.png b/docs/source/usb/img/1.png deleted file mode 100644 index e85ddf7a..00000000 Binary files a/docs/source/usb/img/1.png and /dev/null differ diff --git a/docs/source/usb/img/10.png b/docs/source/usb/img/10.png deleted file mode 100644 index bb57645e..00000000 Binary files a/docs/source/usb/img/10.png and /dev/null differ diff --git a/docs/source/usb/img/11.png b/docs/source/usb/img/11.png deleted file mode 100644 index 11056e33..00000000 Binary files a/docs/source/usb/img/11.png and /dev/null differ diff --git a/docs/source/usb/img/12.png b/docs/source/usb/img/12.png deleted file mode 100644 index 4149d81e..00000000 Binary files a/docs/source/usb/img/12.png and /dev/null differ diff --git a/docs/source/usb/img/13.png b/docs/source/usb/img/13.png deleted file mode 100644 index 29a544b2..00000000 Binary files a/docs/source/usb/img/13.png and /dev/null differ diff --git a/docs/source/usb/img/14.png b/docs/source/usb/img/14.png deleted file mode 100644 index 8ca094a4..00000000 Binary files a/docs/source/usb/img/14.png and /dev/null differ diff --git a/docs/source/usb/img/15.png b/docs/source/usb/img/15.png deleted file mode 100644 index eba7b89b..00000000 Binary files a/docs/source/usb/img/15.png and /dev/null differ diff --git a/docs/source/usb/img/16.png b/docs/source/usb/img/16.png deleted file mode 100644 index 259336ca..00000000 Binary files a/docs/source/usb/img/16.png and /dev/null differ diff --git a/docs/source/usb/img/17.png b/docs/source/usb/img/17.png deleted file mode 100644 index c42de390..00000000 Binary files a/docs/source/usb/img/17.png and /dev/null differ diff --git a/docs/source/usb/img/18.png b/docs/source/usb/img/18.png deleted file mode 100644 index f08b6354..00000000 Binary files a/docs/source/usb/img/18.png and /dev/null differ diff --git a/docs/source/usb/img/19.png b/docs/source/usb/img/19.png deleted file mode 100644 index 2e6eb9ce..00000000 Binary files a/docs/source/usb/img/19.png and /dev/null differ diff --git a/docs/source/usb/img/2.png b/docs/source/usb/img/2.png deleted file mode 100644 index 5b4f5f20..00000000 Binary files a/docs/source/usb/img/2.png and /dev/null differ diff --git a/docs/source/usb/img/20.png b/docs/source/usb/img/20.png deleted file mode 100644 index a44898a8..00000000 Binary files a/docs/source/usb/img/20.png and /dev/null differ diff --git a/docs/source/usb/img/21.png b/docs/source/usb/img/21.png deleted file mode 100644 index 7aa81e95..00000000 Binary files a/docs/source/usb/img/21.png and /dev/null differ diff --git a/docs/source/usb/img/22.png b/docs/source/usb/img/22.png deleted file mode 100644 index 370d39f9..00000000 Binary files a/docs/source/usb/img/22.png and /dev/null differ diff --git a/docs/source/usb/img/23.png b/docs/source/usb/img/23.png deleted file mode 100644 index e08db16e..00000000 Binary files a/docs/source/usb/img/23.png and /dev/null differ diff --git a/docs/source/usb/img/24.png b/docs/source/usb/img/24.png deleted file mode 100644 index fec98d49..00000000 Binary files a/docs/source/usb/img/24.png and /dev/null differ diff --git a/docs/source/usb/img/25.png b/docs/source/usb/img/25.png deleted file mode 100644 index 9bcaf151..00000000 Binary files a/docs/source/usb/img/25.png and /dev/null differ diff --git a/docs/source/usb/img/26.png b/docs/source/usb/img/26.png deleted file mode 100644 index d439b7c4..00000000 Binary files a/docs/source/usb/img/26.png and /dev/null differ diff --git a/docs/source/usb/img/27.png b/docs/source/usb/img/27.png deleted file mode 100644 index 1047da1b..00000000 Binary files a/docs/source/usb/img/27.png and /dev/null differ diff --git a/docs/source/usb/img/28.png b/docs/source/usb/img/28.png deleted file mode 100644 index 95b760c5..00000000 Binary files a/docs/source/usb/img/28.png and /dev/null differ diff --git a/docs/source/usb/img/29.png b/docs/source/usb/img/29.png deleted file mode 100644 index 09538d16..00000000 Binary files a/docs/source/usb/img/29.png and /dev/null differ diff --git a/docs/source/usb/img/3.png b/docs/source/usb/img/3.png deleted file mode 100644 index b8ef0823..00000000 Binary files a/docs/source/usb/img/3.png and /dev/null differ diff --git a/docs/source/usb/img/30.png b/docs/source/usb/img/30.png deleted file mode 100644 index d3014f95..00000000 Binary files a/docs/source/usb/img/30.png and /dev/null differ diff --git a/docs/source/usb/img/4.png b/docs/source/usb/img/4.png deleted file mode 100644 index f80c5366..00000000 Binary files a/docs/source/usb/img/4.png and /dev/null differ diff --git a/docs/source/usb/img/5.png b/docs/source/usb/img/5.png deleted file mode 100644 index ec6a4ba2..00000000 Binary files a/docs/source/usb/img/5.png and /dev/null differ diff --git a/docs/source/usb/img/6.png b/docs/source/usb/img/6.png deleted file mode 100644 index 2d280398..00000000 Binary files a/docs/source/usb/img/6.png and /dev/null differ diff --git a/docs/source/usb/img/7.png b/docs/source/usb/img/7.png deleted file mode 100644 index e7562f11..00000000 Binary files a/docs/source/usb/img/7.png and /dev/null differ diff --git a/docs/source/usb/img/8.png b/docs/source/usb/img/8.png deleted file mode 100644 index a4ac6ad4..00000000 Binary files a/docs/source/usb/img/8.png and /dev/null differ diff --git a/docs/source/usb/img/9.png b/docs/source/usb/img/9.png deleted file mode 100644 index a8b5b2a3..00000000 Binary files a/docs/source/usb/img/9.png and /dev/null differ diff --git a/docs/source/usb/img/overview1.png b/docs/source/usb/img/overview1.png deleted file mode 100644 index fbaf5a19..00000000 Binary files a/docs/source/usb/img/overview1.png and /dev/null differ diff --git a/docs/source/usb/img/overview2.png b/docs/source/usb/img/overview2.png deleted file mode 100644 index c8b3b779..00000000 Binary files a/docs/source/usb/img/overview2.png and /dev/null differ diff --git a/docs/source/usb/img/usb_enum.png b/docs/source/usb/img/usb_enum.png deleted file mode 100644 index 01c67c15..00000000 Binary files a/docs/source/usb/img/usb_enum.png and /dev/null differ diff --git a/docs/source/usb/img/usb_request.png b/docs/source/usb/img/usb_request.png deleted file mode 100644 index bb9f2637..00000000 Binary files a/docs/source/usb/img/usb_request.png and /dev/null differ diff --git a/docs/source/usb/img/usbstruct.png b/docs/source/usb/img/usbstruct.png deleted file mode 100644 index bd062ca3..00000000 Binary files a/docs/source/usb/img/usbstruct.png and /dev/null differ diff --git a/docs/source/usb/usb2.0_basic.rst b/docs/source/usb/usb2.0_basic.rst deleted file mode 100644 index 1c2b599e..00000000 --- a/docs/source/usb/usb2.0_basic.rst +++ /dev/null @@ -1,296 +0,0 @@ -USB 基本概念(2.0 为主) -=========================== - -本文主要对 USB 官方手册 `usb2.0.pdf `_ 中提供的第五章、第七章、第八章、第九章进行讲解。 -如果是初学 usb 的同学,推荐先不要看本节,而是将示例 demo 能够跑通了,熟悉了使用,再来看。 - -简介 ---------- - -USB 是什么?干什么用的?有什么优点?这些大家可以百度,我就不提了。主要先说 USB 的接口和速度根据不同的 USB 版本的分类,如图所示: - -.. figure:: img/overview1.png - -其次是 USB 需要满足的电平标准,有了电平标准后,下面说的信号状态就可以进行分类了。USB2.0 和 USB3.0 支持的电压范围和最大电流如下: - -.. figure:: img/overview2.png - -USB 信号状态 ------------------ - -首先我们需要了解的是 USB 的电气特性中的 Signaling Level,也就是信号状态。USB 主要是靠 D+ 和 D- 来实现不同的信号状态,然后进行通信。官方手册 7.1.7 中列举出了低速、全速和高速时的信号状态对应的 D+ 和 D- 需要满足的要求。 - -.. figure:: img/1.png -.. figure:: img/2.png -.. figure:: img/3.png - -- **差分 0 和差分 1**: 这两个状态用于通过 USB 进行的通用数据通信。当 D+线为高电平、 D-线为低电平时,该状态为差分 1。当 D+线为低电平、 D-线为高电平时,该状态为差分 0。 -- **J 状态和 K 状态**: 除了差分信号外, USB 规范还定义了其他两个差分状态: J 状态和 K 状态。它们的定义由设备速度决定。在全速和高速设备上, J 状态为差分 1 而 K 状态是差分 0。在低速设备上,该情况则相反。 -- **单端 0( SE0)**: 在 D+和 D-均为低电平时所发生的状态。该状态表示一个复位、断连或数据包的结束。 -- **单端 1( SE1)**: 在 D+和 D-均为高电平时发生的状态。不会故意生成该状态,并且不能在 USB 设计中出现。 -- **闲置**: 必须在发送一个数据包的前后发生的状态。如果一个数据线为低电平,而另一个数据线为高电平,则表示闲置状态。高电平和低电平的定义由设备的速度决定。在全速设备上,闲置状态是指 D+为高电平、 D-为低电平。在低速设备上,该情况则相反。 -- **恢复**: 用于使设备从挂起状态唤醒。通过发送一个 K 状态实现该操作。 -- **数据包的开始( SOP)**: 当 D+和 D-线从闲置状态转换到 K 状态时,将在开始低速或全速数据包前发生。 -- **数据包的结束( EOP)**: 在低速或全速数据包结束时发生。当 SE0 状态持续两位时间(后面的内容将介绍位时间)以及 J 状态持续 1 位时间时,将发生 EOP。 -- **复位**: 在 SE0 状态持续 10 ms 时发生。在 SE0 至少持续 2.5 ms 后,该设备会复位,并开始进入复位状态。 -- **保持活动( Keep Alive)**: 在低速设备中使用的信号。低速设备缺少了一个帧起始数据包(用于防止挂起状态)。每次经过 1 ms,它们都会使用一个 EOP 来防止设备进入挂起状态。 - -.. note::这里需要注意的一点就是, J K状态和差分0/1,对于低速来说,和全速/高速是相反的。 - -下面我们通过一个波形,来区分这些信号状态: - -.. figure:: img/4.png - -- 第一个红框,可以看出是一个数据包的开始,并且假设这是一个全速设备,那么D+ 为高,D- 为低,是一个闲置状态。 -- 第二个红框,D+为低,D- 为高,说明是一个 K 状态,由 闲置转 K 状态说明他是一个 SOP。 -- 第三个红框开始表示数据,表示 JKJKJKJKJK。 -- 第四个红框表示 SE0 ,因为D+和 D-均为低电平。 -- 第五个红框,而 SE0 持续了一段时间后,变成了 D+高,D- 低,说明他是一个 J 状态,从 SE0 切换成 J 状态,说明他是一个 EOP。 - -USB 速度识别 ---------------------- - -USB 的速度是如何判定的? 这个见手册 7.1.5.1。USB 的速度检测主要是靠 D+ 和 D-线上拉 1.5K决定,如果 D+上拉1.5k,则该设备为全速设备,如果 D-上拉1.5k,则为低速设备。而高速设备初始是以一个全速设备的身份出现,和全速设备一样,D+线上有一个1.5k的上拉电阻。USB2.0的hub把它当作一个全速设备,之后,hub 和设备通过一系列握手信号确认双方的身份,最终判定该设备为高速设备。 - -.. figure:: img/5.png - -USB 连接与断开检测 ---------------------- - -那么 当我们的设备插上 USB 主机时,主机是如何知道有设备插入或者拔出呢?手册 7.1.7.3 给出了答案,如图所示: - -.. figure:: img/6.png -.. figure:: img/7.png - -首先是连接检测,主机检测到某一个数据线电平拉高保持了一段时间,就认为有设备连接上来了。低速设备连接时,主机会检测到D-线被拉高,全速/高速设备连接时,主机会检测到D+线被拉高。 -而断开检测,则是主机端D+、D-数据线上的下拉电阻起作用,断开后使得二者都在低电平;当低电平持续 TDDIS 时间就会被主机认为是断开状态。上图中,TDDIS在2到2.5us之间。 - -USB 电源 ---------------------- - -作为 USB 电源时, USB 设备可被划分为两种设备类型:总线供电和自供电。 - -- 总线供电是 USB 设计的一个优势。由于设备通过总线供电,因此不需要使用笨重的内部或外部电源,它仍能够维持自身操作。总线可由主机或集线器供电。使用某个总线供电的设备时,用户将设备配置为某种状态前必须考虑其功耗。 -- 自供电设备通过使用外部电源(如直流电源适配器或电池)为自己供电。自供电设备在进行设计的过程中需要考虑到一些注意事项。 USB 规范要求自供电设备一直监控自己的 VBUS 线。 VBUS 不存在的时间内,设备必须断开提供给 D+/D-线上的上拉电阻的电源,从而防止向主机或集线器供电。 否则,会导致 USB 合规性测试发生失败。但是自供电集线器能够从总线获得最多 100 mA 的电流。 - -USB 设备状态 ---------------------- - -在 USB 插上主机的那一刻, USB 设备本身的设备状态是会变化的。而这个设备状态,后面如果学习到枚举过程,可以知道,其实这段变化描述的就是枚举过程。这部分见手册 9.1.1。 - -.. figure:: img/9.png - -- 连接状态: 当将某个设备插入到主机/集线器,但主机/集线器不给 VBUS 线供电时,会出现这种状态。它通常在集线器检测到一个过流事件时出现。虽然仍连接着设备,但主机移除了供给它的电源。 -- 供电: 某个设备被连接到 USB 上并得到供电,但仍未接收到一个复位请求。 -- 默认: 某个设备被连接到 USB 上、得到供电,并且由主机进行了复位。这时,设备没有任何设备地址。 设备会响应地址 0。 -- 地址: 某个设备被连接到 USB、得到供电、被复位,并且有一个唯一的地址。但是设备仍未得到配置。 -- 配置: 设备已经连接到 USB、得到供电、被复位、具有唯一的地址、得到配置,但尚未进入挂起状态。此时,总线供电设备能够消耗超过 100 mA 的电流。 -- 挂起: 如上面所述,设备已经建立好了连接,并且得到配置,但在 3 ms 时间内不会进行任意总线操作。 - -翻译成中文图就是: - -.. figure:: img/10.png - -USB 编码与位填充 ---------------------- - -首先,USB 的数据是串行发送的,就像 UART、I2C、SPI 等等,连续的01 信号只通过一根数据线发送给接受者。但是因为发送者和接收者运行的频率不一样,信号的同步就是个问题,比如,接受者接收到了一个持续一段时间的低电平,无法得知这究竟是代表了 5 个 0 还是 1000 个 0。一个解决办法,就是在传输数据信号的同时,附加一个时钟信号,用来同步两端的传输,接受者在时钟信号的辅助下对数据信号采样,就可以正确解析出发送的数据了,比如 I2C 就是这样做的,SDA 来传输数据,SCL 来传输同步时钟: - -.. figure:: img/11.png - -虽然这样解决了问题,但是却需要附加一根时钟信号线来传输时钟。因为USB没有时钟信号,有没有不需要附加的时钟信号,也能保持两端的同步呢? -有的,这就是 RZ 编码(Return-to-zero Code),也叫做归零编码。 - -RZ 编码(Return-to-zero Code) -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -RZ 编码(Return-to-zero Code),也叫做归零编码。在 RZ 编码中,正电平代表逻辑 1,负电平代表逻辑 0,并且,每传输完一位数据,信号返回到零电平,也就是说,信号线上会出现 3 种电平:正电平、负电平、零电平。 - -.. figure:: img/12.png - -从图上就可以看出来,因为每位传输之后都要归零,所以接受者只要在信号归零后采样即可,这样就不在需要单独的时钟信号。实际上, RZ 编码就是相当于把时钟信号用归零编码在了数据之内。这样的信号也叫做自同步(self-clocking)信号。 -这样虽然省了时钟数据线,但是还是有缺点的,因为在 RZ 编码中,大部分的数据带宽,都用来传输“归零”而浪费掉了。 - -NRZ 编码(Non-return-to-zero Code) -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -去掉这个归零步骤,NRZ 编码(Non-return-to-zero Code)就出现了,和 RZ 的区别就是 NRZ 是不需要归零的。 - -.. figure:: img/13.png - -NRZI 编码(Non-Return-to-Zero Inverted Code) -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -NRZI 编码(Non-Return-to-Zero Inverted Code)和 NRZ 的区别就是 NRZI 用信号的翻转代表一个逻辑,信号保持不变代表另外一个逻辑。这个见手册 7.1.8。 - -.. figure:: img/14.png - -如图所示,可以得出一个简单的记忆方式:遇到 0 的边沿电平就翻转,遇到 1 的边沿则不变。 - -位填充(bit-stuffing) -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -但是,这样还是会有一个问题,就是虽然接受者可以主动和发送者的频率匹配,但是两者之间总会有误差。假如数据信号是 1000 个逻辑 1,经过 USB 的 NRZI 编码之后,就是很长一段没有变化的电平,在这种情况下,即使接受者的频率和发送者相差千分之一,就会造成把数据采样成 1001 个或者 999 个 1了。 -USB 对这个问题的解决办法,就是强制插 0,也就是(位填充)bit-stuffing,如果要传输的数据中有 6个连续的 1,发送前就会在第 6 个 1 后面强制插入一个 0,让发送的信号强制出现翻转,从而强制接受者进行频率调整。 -接受者只要删除 6 个连续 1 之后的 0,就可以恢复原始的数据了。这部分见手册 7.1.9。 - -.. figure:: img/15.png -.. figure:: img/16.png -.. figure:: img/17.png - -在数据被NRZI编码之前,在数据流中每六个连续的1之后插入一个0,以强制NRZI数据流中的过渡,这使接收器逻辑至少每七位有一次数据转换,以保证数据和时钟的锁定。比特填充是从同步模式开始启用。结束同步模式的数据 "一 "被算作是序列中的第一个 "一"。序列中的第一个。除了高速EOP期间,发射器的位填充总是被强制执行。如果需要按照 -位填充规则的要求,零位将被插入,即使它是数据包结束(EOP)信号前的最后一位。接收器必须对NRZI数据进行解码,识别填充位,并将其丢弃。 - -.. caution:: 以下内容可以用一张图概括,了解即可,没有必要死记硬背 - -.. figure:: img/usbstruct.png - -USB 字段(域) ---------------------- - -USB 字段构成了 USB 通信中最基本也是最小的单元,后面的包、事务,最根本都是由字段构成,而字段又是由比特构成。字段部分见手册 8.1。 - -.. note:: USB 的比特先行模式是按照 LSB 先行原则。 - -同步字段 -^^^^^^^^^^^^^^^^^^^^^^^^ - -在 USB 系统中,主机和设备不是共享一个时钟,这使得接收方没办法准确知道发送方什么时候发送数据,尽管能检测到SOP,但是远远不够,所有这个时候就需要同步字段,使得接收方和发送方收发过程中保持同步,所以任何一个包都要以同步字段开始。同步字段0x01,经过编码以后就是01010100B。 - -.. figure:: img/18.png - -包标识符字段 -^^^^^^^^^^^^^^^^^^^^^^^^ - -PID 由一个四位数据包类型字段和一个四位校验字段组成,占用 8 个bit,如图所示。 PID指示数据包的类型,并通过推断,数据包的格式和应用于数据包的错误检测类型包。 PID的四位校验字段是通过执行分组类型字段的一个补码来生成,从而确保PID的可靠解码,以便正确解释分组的其余部分,如果四个PID校验位不是它们各自的分组标识符位的补码,则存在PID错误。 - -.. figure:: img/19.png - -既然是 4个比特,说明了 PID 类型可以分为16种,从16种中,又细分成4类:令牌 PID,数据 PID,握手 PID 和特殊 PID。 - -.. figure:: img/20.png - -地址字段 -^^^^^^^^^^^^^^^^^^^^^^^^ - -地址字段又分为设备地址字段和端点地址字段,其中设备地址字段占用 7 个bit,除去0 地址,主机可以分配的地址有 127个。 - -.. figure:: img/21.png - -端点地址字段占用 4个 bit,总共可以提供 16 个端点。 - -.. figure:: img/22.png - -帧号字段 -^^^^^^^^^^^^^^^^^^^^^^^^ - -帧号字段占用 11 个bit,主机每发出一个帧,帧号都会加1,如图所示。而高速设备中,帧中又包含微帧,1帧=8微帧,微帧则是加0.1。关于帧和微帧的概念,后续补充。 - -.. figure:: img/23.png - -数据字段 -^^^^^^^^^^^^^^^^^^^^^^^^ - -根据传输类型不同,数据字段中的数据长度也是不定的,从 0-1024不等。 - -.. figure:: img/24.png - -CRC 字段 -^^^^^^^^^^^^^^^^^^^^^^^^ - -循环冗余校验(CRC)用于保护令牌和数据包中的所有非PID字段。PID不包含在包含CRC的分组的CRC校验中。 在执行比特填充之前,在发送器中的各个字段上生成所有CRC。 类似地,在去除填充位之后,在接收器中对CRC进行解码。令牌和数据包CRC为所有单比特和双比特错误提供100%的覆盖。 CRC失败被认为表示一个或多个受保护字段已损坏并导致接收器忽略这些字段,并且在大多数情况下,忽略整个数据包。 - -.. figure:: img/24.png - -- 令牌CRC - -为令牌提供五位CRC字段,并覆盖IN,SETUP和OUT令牌的ADDR和ENDP字段或SOF令牌的时间戳字段。 PING和SPLIT特殊令牌还包括一个五位CRC字段。 - -生成多项式为: G(X)= X^5 + X^2 + 1 -表示该多项式的二进制位模式是00101B。 如果接收到所有令牌位而没有错误,则接收器处的五位校验和将为01100B。 - -- 数据CRC - -数据CRC是应用于数据分组的数据字段的16位多项式。 - -生成多项式是:G(X)= X^16 + X^15 + X^2 + 1 -表示该多项式的二进制位模式是1000000000000101B。 如果没有错误地接收到所有数据和CRC位,则16位校验和将为1000000000001101B。 - -USB 包 ---------------------- - -包由字段组成,根据 PID 类型,包分为四大类:令牌包、数据包、握手包、特殊包。此节内容见官方 8.4.1。 - -.. figure:: img/25.png - -算上 SOP,则如图,组成一个完整的包。 - -.. figure:: img/26.png - -令牌包 -^^^^^^^^^^^^^^^^^^^^^^^^ - -令牌包分为:SETUP、IN、OUT、SOF,其中 SETUP、IN、OUT的字段组成一样,如图: - -.. figure:: img/27.png - -- PID 字段:定义了数据传输方向为USB主机到USB设备。 -- ADDR 字段:指明了USB设备地址。 -- ENDP 字段:指明了接收数据的端点号。 -- CRC 字段:用于ADDR字段和ENDP字段进行循环冗余校验。 - -SOF 包的字段组成,如图: - -.. figure:: img/28.png - -- PID 字段:定义了数据传输方向为USB主机到USB设备。 -- 帧号 字段:指明了USB传输的帧号,其11位。 -- CRC 字段:用于ADDR字段和ENDP字段进行循环冗余校验。 - -数据包 -^^^^^^^^^^^^^^^^^^^^^^^^ - -.. figure:: img/29.png - -- PID 字段:用于指明不同的数据包类型。支持 4 种数据包,分别为: DATAO 、 DATA1 、DATA2 和MDATA。 -- 数据 字段:其中包含了传输的数据。其数据的大小根据数据传输类吧和川户需要而定。根据 USB 协议的规定,对于低速 USB 数据传输, 最大长度为8字节对于全速SB 数据传输,其最大长度为 1023 字节;对于高速 USB 数据传输,数据最大长度为 1024 。 -- CRC 字段:这里使用 16 位的循环冗余校验来对数据字段进行保护。 - -握手包 -^^^^^^^^^^^^^^^^^^^^^^^^ - -握手包由8位的PID构成,用于数据传输的末位报告本次数据传输的状成。握手包之后使是整个事务处理的结束信号EOP. - -.. figure:: img/30.png - -特殊包 -^^^^^^^^^^^^^^^^^^^^^^^^ - -USB 事务 ---------------------- - -USB 常用事务共有三种:SETUP、IN、OUT,除了控制传输使用三个事务,其他传输都使用两个事务。特殊事务则是不携带数据的事务。 - -SETUP 事务 -^^^^^^^^^^^^^^^^^^^^^^^^ - -IN 事务 -^^^^^^^^^^^^^^^^^^^^^^^^ - -OUT 事务 -^^^^^^^^^^^^^^^^^^^^^^^^ - -特殊事务 -^^^^^^^^^^^^^^^^^^^^^^^^ - -USB 传输 ---------------------- - -控制传输 -^^^^^^^^^^^^^^^^^^^^^^^^ - -批量传输 -^^^^^^^^^^^^^^^^^^^^^^^^ - -中断传输 -^^^^^^^^^^^^^^^^^^^^^^^^ - -同步传输 -^^^^^^^^^^^^^^^^^^^^^^^^ \ No newline at end of file diff --git a/docs/source/usb/usb3.0_basic.rst b/docs/source/usb/usb3.0_basic.rst deleted file mode 100644 index 1dbbd815..00000000 --- a/docs/source/usb/usb3.0_basic.rst +++ /dev/null @@ -1,33 +0,0 @@ -USB 基本概念(3.0 为主) -=========================== - - -简介 ------------- - - - -与 USB 2.0 相同和不同点 --------------------------- - - -Link Layer --------------------- - -LCW -^^^^^^^^^^ - -Protocol Layer --------------------- - -LMP -^^^^^^^^^^^^^^^^^^^^^^^^ - -TP -^^^^^^^^^^^^^^^^^^^^^^^^ - -DP -^^^^^^^^^^^^^^^^^^^^^^^^ - -ITP -^^^^^^^^^^^^^^^^^^^^^^^^ \ No newline at end of file diff --git a/docs/source/usb/usb_desc.rst b/docs/source/usb/usb_desc.rst deleted file mode 100644 index f0bcc7fe..00000000 --- a/docs/source/usb/usb_desc.rst +++ /dev/null @@ -1,37 +0,0 @@ -USB 描述符 -=========================== - -本节参考官方 usb2.0 pdf 9.5 节即可。 - -设备描述符 ---------------------- - -配置描述符 ---------------------- - -接口描述符 ---------------------- - -端点描述符 ---------------------- - -字符串描述符 ---------------------- - -接口关联描述符 ---------------------- - -设备限定描述符 ---------------------- - -其他速度描述符 ---------------------- - -BOS 描述符 ---------------------- - -超高速端点伴随描述符 ---------------------- - -增加型超高速同步端点伴随描述符 -------------------------------- diff --git a/docs/source/usb/usb_enum.rst b/docs/source/usb/usb_enum.rst deleted file mode 100644 index 1434424f..00000000 --- a/docs/source/usb/usb_enum.rst +++ /dev/null @@ -1,22 +0,0 @@ -USB 枚举 -=========================== - -当我们了解了 usb 设备请求以后,就可以来学习下 USB 设备的整个枚举过程了,看看是如何枚举出一个串口、鼠标、u盘等设备了。枚举过程中主机会发送设备请求来获取相关信息(也就是描述符),具体发送哪些,参考下图。 - -.. figure:: img/usb_enum.png - -- 首先设备接上 USB 线,然后插上电脑 -- 设备插上以后上电,处于供电状态 -- 主机通过 D+/D- 识别到设备插入 -- 对设备进行复位 -- 主机发送 **获取设备描述符请求** -- 可选的复位操作 -- 主机发送 **设置设备地址请求** -- 主机发送 **获取配置描述符请求**,可能会获取多次,无所谓 -- 主机发送 **获取字符串描述符请求**,正常会获取3个字符串,如果后面的描述符中指定了字符串,则继续获取指定的字符串 -- 主机发送 **获取设备限定描述符请求**,用来获取在设备工作在其他速度上的请求,如果设备只能工作在全速模式,则必须回复 stall,并且协议栈中一定会打印该请求告诉你此命令设备不支持。 -- 主机发送 **设置配置请求**,对设备的端点进行配置,通常是根据端点描述符中的配置进行设置。 -- 到此标准的设备请求结束 -- 主机根据接口描述符加载对应支持的 class 驱动,如果主机不支持,则会提示该设备找不到驱动 -- 加载完成以后,开始执行该 class 相关的请求 -- 最终进行 class 的数据流传输 \ No newline at end of file diff --git a/docs/source/usb/usb_ext.rst b/docs/source/usb/usb_ext.rst deleted file mode 100644 index 86b87a53..00000000 --- a/docs/source/usb/usb_ext.rst +++ /dev/null @@ -1,39 +0,0 @@ -.. _usb_ext: - -USB 知识点拓展 -=========================== - -什么是分包 -------------- - -由于 USB 协议中规定了每个包的最大长度,所以当我们发送的数据长度超过了最大包长度时,就需要分包发送,这就是分包。比如 ep mps 为 64,数据长度为 129,则 USB 会按照 64 + 64 + 1 的形式传输。 -而对于 USB IP 来说,分包分为软件分包和硬件分包,软件分包就是用户代码自行分包,这种 ip 一般都使用 FIFO 来进行,因为 FIFO 深度是有限的;第二种 -则是使用硬件分包,这种 USB IP 一般带 DMA 或者描述符 DMA 功能,那么这种 IP 的效率无疑是最高的,cherryusb 中充分利用了这点,使得 USB 速度能够达到最高。 - -对于软件分包来说,一次发送的长度即使是 16K, **内部也是通过软件分包的,在这种情况下,发送长度的多少不会对速度有任何提升**。 -对于硬件分包来说,发送的长度会影响速度,因为硬件分包是通过 DMA 来进行的, **一次发送的长度越大,DMA 的效率就越高,速度也就越快**。(当然,其他协议栈虽然使用了 dma,但是部分代码实现还是按照一个包进行,等于没用,这也是速度低的一个原因) - -什么是短包 ----------------- - -在上面我们讲了分包之后,短包就是分包的最后一个包(并且长度小于 EP MPS).比如发送 129 字节的数据,那么 USB 会按照 64 + 64 + 1 的形式传输,最后一个包是1个字节,这1个字节就是短包。 - -什么是 ZLP -------------- - -ZLP,顾名思义,零长度数据包,也就是数据长度为0 的短包。是 USB 设备在数据传输结束时,如果数据长度正好是最大包长度的整数倍,那么就需要发送一个 ZLP 数据包,用来告诉对方数据传输结束。 - -.. caution:: ZLP 功能仅限于 CONTROL 和 BULK 传输 - -什么时候算中断完成 --------------------- - -从机接收:接收的长度与设置的长度相等;接收的最后一个包为短包。 -从机发送:发送的长度与设置的长度相等,如果发送的长度是 EP MPS 的整数倍, **通常** 需要再发送一个 ZLP(仅限 control 和 bulk 传输)。 - -.. note:: 对于从机接收,并且是 bulk 传输,接收长度通常设计为 EP MPS,以下三种情况可以修改为多个 EP MPS: 固定长度;自定义协议并携带长度(例如 MSC); 主机手动发送 ZLP 或者短包(例如 RNDIS) - -.. note:: 对于从机发送,并且是 bulk 传输,发送长度没有限制,但是如果是 EP MPS 整数倍,通常需要发送 ZLP。自定义协议则不需要发送 ZLP,例如 MSC。 - -主机接收:同从机接收 -主机发送:发送的长度与设置的长度相等 diff --git a/docs/source/usb/usb_request.rst b/docs/source/usb/usb_request.rst deleted file mode 100644 index 8e42565d..00000000 --- a/docs/source/usb/usb_request.rst +++ /dev/null @@ -1,6 +0,0 @@ -USB 设备请求 -=========================== - -本节参考官方 usb2.0 pdf 9.3、9.4 节即可。 - -.. figure:: img/usb_request.png diff --git a/docs/source/usbdev.svg b/docs/source/usbdev.svg deleted file mode 100644 index 8f787289..00000000 --- a/docs/source/usbdev.svg +++ /dev/null @@ -1,4 +0,0 @@ - - - -
usbd_desc_register
usbd_add_interface
usbd_add_endpoint
    struct usbd_tx_rx_msg tx_msg[16];
    struct usbd_tx_rx_msg rx_msg[16];
struct usbd_interface *intf[16];
usbd_initialize
USBD_IRQHandler
usbd_event_reset_handler
usbd_event_ep0_setup_complete_handler
usbd_event_ep_in_complete_handler
usbd_event_ep_out_complete_handler
usbd_setup_request_handler
tx_msg[ep & 0x7f].cb
rx_msg[ep & 0x7f].cb
usbd_event_ep0_in_complete_handler
tx_msg[ep & 0x7f].cb (ep != 0)
usbd_event_ep0_out_complete_handler
rx_msg[ep & 0x7f].cb (ep != 0)
usbd_standard_request_handler
usbd_class_request_handler
usbd_vendor_request_handler
\ No newline at end of file diff --git a/docs/source/usbhost.svg b/docs/source/usbhost.svg deleted file mode 100644 index b7d537b5..00000000 --- a/docs/source/usbhost.svg +++ /dev/null @@ -1,9 +0,0 @@ -
usbh_initialize
usbh_initialize
usbh_hub_initialize
usbh_hub_initialize
usbh_roothub_register
usbh_roothub_register
create usbh_hub_thread
create usbh_hub_thread
usb_hc_init
usb_hc_init
usbh_roothub_thread_wakeup
usbh_roothub_thread_wakeup -
hub_int_complete_callback
hub_int_complete_callback -
wakeup
wakeup
wakeup
wakeup
usbh_enumerate
usbh_enumerate -
search all ports
search all ports
usbh_hub_events
usbh_hub_events -
CLASS_CONNECT
CLASS_CONNECT -
search all interface drivers
search all interface drivers
usbh_find_class_driver
usbh_find_class_driver -
if hub class?
if hub class?
usbh_int_urb_fill


usbh_submit_urb
usbh_int_urb_fill...
Class Register
Class Register -
USBH_IRQHandler
USBH_IRQHandler -
Viewer does not support full SVG 1.1
\ No newline at end of file diff --git a/docs/source/usbip/cdns2.rst b/docs/source/usbip/cdns2.rst deleted file mode 100644 index 88afc8d2..00000000 --- a/docs/source/usbip/cdns2.rst +++ /dev/null @@ -1,2 +0,0 @@ -CDNS2 -=============== diff --git a/docs/source/usbip/cdns3.rst b/docs/source/usbip/cdns3.rst deleted file mode 100644 index c2132d1a..00000000 --- a/docs/source/usbip/cdns3.rst +++ /dev/null @@ -1,2 +0,0 @@ -CDNS3 -=============== diff --git a/docs/source/usbip/chipidea.rst b/docs/source/usbip/chipidea.rst deleted file mode 100644 index 57c46ec0..00000000 --- a/docs/source/usbip/chipidea.rst +++ /dev/null @@ -1,2 +0,0 @@ -CHIPIDEA -================= \ No newline at end of file diff --git a/docs/source/usbip/dwc2.rst b/docs/source/usbip/dwc2.rst deleted file mode 100644 index 6c5a8c08..00000000 --- a/docs/source/usbip/dwc2.rst +++ /dev/null @@ -1,2 +0,0 @@ -DWC2 -================= \ No newline at end of file diff --git a/docs/source/usbip/dwc3.rst b/docs/source/usbip/dwc3.rst deleted file mode 100644 index 746bbee6..00000000 --- a/docs/source/usbip/dwc3.rst +++ /dev/null @@ -1,2 +0,0 @@ -DWC3 -=============== diff --git a/docs/source/usbip/ehci.rst b/docs/source/usbip/ehci.rst deleted file mode 100644 index 637bbe69..00000000 --- a/docs/source/usbip/ehci.rst +++ /dev/null @@ -1,2 +0,0 @@ -EHCI -================= \ No newline at end of file diff --git a/docs/source/usbip/fotg210.rst b/docs/source/usbip/fotg210.rst deleted file mode 100644 index f6e566a8..00000000 --- a/docs/source/usbip/fotg210.rst +++ /dev/null @@ -1,2 +0,0 @@ -FOTG210 -=============== diff --git a/docs/source/usbip/musb.rst b/docs/source/usbip/musb.rst deleted file mode 100644 index 597876c0..00000000 --- a/docs/source/usbip/musb.rst +++ /dev/null @@ -1,2 +0,0 @@ -MUSB -================= \ No newline at end of file diff --git a/docs/source/usbip/ohci.rst b/docs/source/usbip/ohci.rst deleted file mode 100644 index 8467233b..00000000 --- a/docs/source/usbip/ohci.rst +++ /dev/null @@ -1,2 +0,0 @@ -OHCI -================= \ No newline at end of file diff --git a/docs/source/usbip/xhci.rst b/docs/source/usbip/xhci.rst deleted file mode 100644 index 0c16c2e2..00000000 --- a/docs/source/usbip/xhci.rst +++ /dev/null @@ -1,2 +0,0 @@ -XHCI -================= \ No newline at end of file diff --git a/docs/source/version.rst b/docs/source/version.rst deleted file mode 100644 index 5c6e23e7..00000000 --- a/docs/source/version.rst +++ /dev/null @@ -1,182 +0,0 @@ -版本说明 -============================== - -如果没有特别情况,请使用最新版本。下面只列举比较重要的更新,详细更新说明请参考 https://github.com/cherry-embedded/CherryUSB/releases。 - -<= v0.10.2 初代版本 ----------------------- - -- **用于定基本的主从机框架,仅支持单 USB IP**。 -- **host 驱动每个 ep 占用一个 硬件 pipe,不支持动态使用硬件 pipe**。 -- 相关 porting 需要使用此版本,后续不再支持(比如 ch32,rp2040),以及旧版本pusb2 和 xhci(新版本不再提供源码)。 - -v1.0.0 过度版本 ----------------------- - -- **host 支持动态使用硬件 pipe,不再固定** - -v1.1.0 过度版本 ----------------------- - -- **主从机支持多 USB IP 且要相同 IP** -- **host 增加 bluetooth, ch340, ftdi, cp210x, asix 驱动** -- device msc 支持多 lun,并且 CONFIG_USBDEV_MSC_BLOCK_SIZE 修改为 CONFIG_USBDEV_MSC_MAX_BUFSIZE - -v1.2.0 ----------------------- - -- **host 增加 rtl8152,cdc ncm 驱动** -- host 增加 timer 去控制中断传输(hub修改为 timer 控制) -- porting 增加 esp,aic 主机驱动 -- **优化 DWC2 优化代码方便阅读,并增加一些 FIFO 配置宏给用户(因为 dwc2 fifo 大小有限,以及配置方式很多,所以导出给用户配置,方便合理控制性能)** -- 优化 ehci 驱动(qtd不再使用动态申请,绑定 qh),方便代码运行的更快 - -v1.3.0 ----------------------- - -- **device 支持多种速度描述符自动选择功能(开启 CONFIG_USBDEV_ADVANCE_DESC)** -- device core 代码统一 ep0 buffer 的使用,用于美化代码 -- host 增加 pl2303 驱动;采用 id table 来支持多个 vid,pid;增加 user_data 给用户使用 -- host 网络 class 驱动增加 tx、rx buffer 的宏,增加 LWIP_TCPIP_CORE_LOCKING_INPUT 的使用,以便实现数据的零拷贝 -- porting 导入 bouffalo,aic,stm32f723 device驱动 -- **porting 中主机部分 urb->timeout 清0 的处理有点问题(大数据量传输时会出现 no pipe alloc 异常,主要原因是刚启动传输就完成了,还没判断 timeout就被修改为0了,没有进入 take sem 流程),此版本已修复** -- ehci enable iaad in usbh_kill_urb,read ehci hcor offset from hccr caplength,enable ohci for ehci -- 适配 nuttx os - -v1.3.1 ----------------------- - -- bugfix(audio,video,cdc ecm 相关宏,结构体,api) -- **host hub 枚举线程删除,使用 psc 线程,枚举方式更改为队列模式,取消同时枚举多个设备的功能** -- host 扫描驱动信息和 instance 采用递归模式,删除链表扫描 -- host 网络 class 驱动优化,支持接收 16K 以上的数据(cdc ecm 不支持),采用高级 memcpy api -- **device 协议栈中打印删除(中断中不再做打印)** -- porting 中 musb fifo配置修改为从 fifo table 获取(此代码参考 linux),适配 es32,sunxi,beken - -v1.4.0 ----------------------- - -- **device 开始支持 remote wakeup 功能, hid request(0x21),完善 GET STATUS 请求(此版本开始可以通过 USB3CV 测试)** -- device 增加 UF2, ADB, WEBUSB 功能; msc 增加裸机的读写 polling 功能,将读写放在 while1中执行; usbd_cdc 改名为 usbd_cdc_acm -- host 增加 usbwifi(bl616), xbox驱动; **重构 USB3.0 枚举逻辑** -- **host 中 cdc_acm,hid,msc,serial 传输共享 buffer,如果存在多个相同的设备会有问题,修改为单独的 buffer** -- **porting 重构 XHCI/PUSB2 驱动,不开源**;ehci 和 ohci 文件改名;增加 remote wakeup api -- esp 组件库支持 -- **chipidea 从机驱动支持,nxp mcx 系列主从支持** -- threadx os 支持 - -v1.4.1 ----------------------- - -- **修复device 模式下使用多个 altsetting 时重复关闭端点问题,改成 altsetting 为0时关闭** -- **重构主机 audio 解析描述符** -- **增加 kinetis usbip** -- 主机下 usbh_msc_get_maxlun 请求部分 U 盘不支持,不做错误返回 -- 主机下 usbh_hid_get_report_descriptor 导出给用户调用 -- 静态代码检查 -- github action 功能 - -v1.4.2 ----------------------- - -- device 实现 USB_REQUEST_GET_INTERFACE 请求 -- **device video 传输重构,增加双缓冲功能** -- device ecm 重构,保持和 rndis 类似 API -- device 和 host audio 音量配置功能重构 -- host 增加 AOA 驱动 -- 兼容 C++ 相关修改 -- fsdev 不支持 ISO 和 DWC2 高速 hub 不支持全速低速检查 -- **通用 OHCI 代码更新** - -v1.4.3 ----------------------- - -- **device ep0 处理增加线程模式** -- device audio feedback 宏和demo -- device rndis 增加透传功能(无LWIP) -- **host msc 将 scsi 初始化从枚举线程中移出,在mount阶段调用,并增加了testunity 多次尝试,兼容一部分 U 盘** -- rp2040 主从支持 -- **nuttx fs,serial,net 组件支持** -- dwc2、ehci、ohci 主机 dcache功能支持(v1.5.0 完善) -- t113、MCXA156、CH585 、 **stm32h7r 支持** -- 修复 v1.4.1 中 altsetting 为0时应该关闭所有端点的问题 - -v1.5.0 ----------------------- - -- **协议栈内部全局 buffer 需要使用 USB_ALIGN_UP 对齐, 用于开启 dcache 并且不使能 nocache 时使用** -- **完善 ehci/ohci dcache 模式下的处理**, add CONFIG_USB_EHCI_DESC_DCACHE_ENABLE for qh&qtd&itd, add CONFIG_USB_OHCI_DESC_DCACHE_ENABLE for ed&td -- **平台代码更新,平台相关转移到 platform,增加 lvgl 键鼠支持,blackmagic 支持,filex 支持, zephyr disk支持,esp-idf netif支持** -- **device sof callback 支持** -- **dwc2 、fsdev st 下实现底层 API 和中断,直接调用 HAL_PCD_MSP 和 HAL_HCD_MSP,不需要用户复制粘贴** -- **DWC2 实现 SPLIT 功能,高速模式下支持外部高速 hub 对接 FS/LS 设备** -- liteos-m, zephyr os 支持 -- device msc 裸机读写采用变量模式,而不是ringbuffer -- ehci qtd 使用 qtd alloc & free,节省内存,目前是 qh 携带 qtd -- rndis/ECM device, msc demo 更新,支持 rt-thread 下免修改 -- **memcpy 全部使用 usb_memcpy 替换,arm 库存在非对其访问问题** -- **重构 device mtp 驱动(收费使用)** -- **device tmc 驱动(收费使用)** -- **重构device video 传输,直接在图像数据中填充 uvc header,达到zero memcpy** -- **增加 usb_osal_thread_schedule_other api,用于在释放 class 资源之前,先释放所有 class 线程,避免释放 class 资源以后线程还在使用该 class 资源** -- **dwc2 device 增加 dcache 功能,可用于 cortex-M7/ESP32P4** -- **bouffalo/hpm/esp/st/nxp dcache api 支持** -- ch32 device iso 更新,IP 目录重新分类 -- cmake,scons,kconfig 更新 -- 使用 USB_ASSERT_MSG 对部分代码检查,全面性 warning 修复 -- N32H4/MM32F5 device 支持 -- 默认使能 CONFIG_USBDEV_ADVANCE_DESC - -v1.5.1 ----------------------- - -- 支持 rt-thread 下使用 adb shell,host serial/device cdc_acm 对接 rtdevice 框架 -- **dwc2 增加多个 usbport 不同参数的配置功能,比如一个全速一个高速,fifo配置和phy配置不同** -- **ehci 在控制传输中如果没有 nodata 阶段会导致 data qtd 未释放,导致内存泄漏** -- **dwc2 读取 setup 使用 usbd_get_next_ep0_state 去判断,避免 setup 和 ep0 out 使用在 USB_OTG_DOEPINT_XFRC 状态下冲突** -- sifli usb device 初步支持 - -v1.5.2 ----------------------- - -- 对 1.5.1 下 rt-thread 组件的一些 bugfix -- idf timer osal 替换为 esp timer,freertos timer会有启动失败的可能性;xTaskCreate 使用 xTaskCreatePinnedToCore 替换,方便多核使用 -- 主机枚举中,删除描述符溢出相关的 ASSERT 操作,改成返回错误。获取字符串描述符改成支持才获取。2 ms 延时改成 10ms,因为一些 os 使用的是 100hz,会造成延时失效 -- **dwc2 ep mult 支持,split 传输代码优化,对 split 相关的 cache 处理修改** -- **dwc2 halt 中不能清除 USB_OTG_HCCHAR_EPDIR,reset port 中使用超时机制,防止在枚举时由于拔出而造成死等** -- 更新 DWC2 中 at32,stm32,kendryte,espressif glue 代码 -- musb 对于标准的 IP 结构采用独立 EP 控制寄存器组,不使用 EPIDX 寄存器去控制 -- 删除所有 CONFIG_USBDEV_EP_NUM & CONFIG_USBHOST_PIPE_NUM,不再使用,因为 IP 本身会携带这些信息,或者厂家 SDK 提供了对应的宏 -- CONFIG_USBHOST_MAX_INTF_ALTSETTINGS 默认使用 2 减少内存,只有 UVC 和UAC 使用(商业收费),所以不需要开很大 -- urb interval 从 u8 改 u32,最大支持 2^15 * 125us - -v1.5.3 ----------------------- - -- 增加 mongoose demo -- **从机支持自定义 ep0 mps,仅支持商业性 IP** -- 主机增加 UVC bulk支持, **接口号匹配驱动功能**, **主机分配地址功能改成循环自增模式** ,重构 lsusb 命令 -- 主机控制传输增加 retry 机制,部分 device 通信不稳定,retry 次数参考 linux -- **主机 rndis 驱动增加非标 02/02/ff 接口驱动匹配** -- musb IP 关闭 multipoint feature 支持 -- hpmicro、chipidea dcache 支持 -- idf host msc 支持 -- otg 框架重构,当前 port 仅支持 hpmicro -- CI 编译功能,支持 hpmicro/espressif/bouffalolab - -v1.5.3.99 ----------------------- - -bugfix for v1.5.3 - - -v1.6.0 ----------------------- - -- **host 增加 serial 框架,统一所有类串口驱动** -- **host hid 增加报告描述符解析功能** -- usbh_initialize 增加 event callback,用于通知用户主机事件变化,通常不需要使用,设置为 NULL 即可 -- 支持 gamepad device -- 增加 ti xmc,infineon edge e8x port 支持 -- dwc2 增加 usbd_dwc2_get_system_clock 替换 SystemCoreClock;删除 __UNALIGNED_UINT32_READ 和 __UNALIGNED_UINT32_WRITE 宏;读取 setup 个数设置为 1个;第一次读取 setup 移动到 USB_OTG_GINTSTS_ENUMDNE 中断中 -- dwc2/ehci 增加 roothub 速度设置 \ No newline at end of file diff --git a/docs/zh/.readthedocs.yaml b/docs/zh/.readthedocs.yaml new file mode 100644 index 00000000..e94ddd80 --- /dev/null +++ b/docs/zh/.readthedocs.yaml @@ -0,0 +1,35 @@ +# Read the Docs configuration file for Sphinx projects +# See https://docs.readthedocs.io/en/stable/config-file/v2.html for details + +# Required +version: 2 + +# Set the OS, Python version and other tools you might need +build: + os: ubuntu-22.04 + tools: + python: "3.11" + # You can also specify other tool versions: + # nodejs: "20" + # rust: "1.70" + # golang: "1.20" + +# Build documentation in the "docs/" directory with Sphinx +sphinx: + configuration: docs/zh/conf.py + # You can configure Sphinx to use a different builder, for instance use the dirhtml builder for simpler URLs + # builder: "dirhtml" + # Fail on all warnings to avoid broken references + # fail_on_warning: true + +# Optionally build your docs in additional formats such as PDF and ePub +# formats: +# - pdf +# - epub + +# Optional but recommended, declare the Python requirements required +# to build your documentation +# See https://docs.readthedocs.io/en/stable/guides/reproducible-builds.html +python: + install: + - requirements: docs/requirements.txt \ No newline at end of file diff --git a/docs/zh/api/api_config.rst b/docs/zh/api/api_config.rst new file mode 100644 index 00000000..c1fe8603 --- /dev/null +++ b/docs/zh/api/api_config.rst @@ -0,0 +1,163 @@ +USB CONFIG 说明 +========================= + +通用 CONFIG +--------------------- + +CONFIG_USB_PRINTF +^^^^^^^^^^^^^^^^^^^^ + +USB log 功能,默认重定向到 printf,需要注意,USB log 会在中断中使用,因此重定向的 api 不允许阻塞。举例,如果使用的是 rt-thread,请更换成 rt-kprintf + +CONFIG_USB_DBG_LEVEL +^^^^^^^^^^^^^^^^^^^^^^ + +控制 log 的打印级别 + +CONFIG_USB_PRINTF_COLOR_ENABLE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +控制 log 颜色打印,默认开启 + +CONFIG_USB_DCACHE_ENABLE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +不使用 nocache ram 时,开启此宏以保证数据一致性。 **使用 EHCI 时,内部依旧需要使用 nocache ram**。 + +CONFIG_USB_ALIGN_SIZE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +USB buffer 的对齐大小,默认是 4。IP 在 dma 模式下可能对输入的 buffer有对齐要求,一般是4,如果是其他对齐方式,请修改此值。 + +USB_NOCACHE_RAM_SECTION +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +如果芯片没有 cache 功能,此宏无效。如果有,则 USB 的输入输出 buffer 必须放在 nocache ram 中,保证数据一致性。 + +设备协议栈 CONFIG +--------------------- + +CONFIG_USBDEV_REQUEST_BUFFER_LEN +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +控制传输接收和发送的 buffer 最大长度,默认是 512。 + +CONFIG_USBDEV_SETUP_LOG_PRINT +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +使能或者关闭 setup 包的 dump 信息,默认关闭。 + +CONFIG_USBDEV_DESC_CHECK +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +暂时没有实现 + +CONFIG_USBDEV_TEST_MODE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +使能或者关闭 usb test mode + +CONFIG_USBDEV_MSC_MAX_BUFSIZE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +msc 缓存的最大长度,缓存越大,USB 的速度越高,因为介质一般多个 block 读写速度比单个 block 高很多,比如 sd 卡。 +默认 512 ,如果是 flash 需要改成 4K, 缓存的大小需要是介质的一个 block size 的整数倍。 + +CONFIG_USBDEV_MSC_MANUFACTURER_STRING +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +CONFIG_USBDEV_MSC_PRODUCT_STRING +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +CONFIG_USBDEV_MSC_VERSION_STRING +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +CONFIG_USBDEV_MSC_POLLING +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +将 usbd_msc_sector_read 和 usbd_msc_sector_write 操作放在 while1 中运行,裸机下使用。 + +CONFIG_USBDEV_MSC_THREAD +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +使能或者关闭 msc 线程,默认关闭。usbd_msc_sector_read 和 usbd_msc_sector_write 默认是在中断中执行,所以如果开启了 os 建议开启此宏,那么, +usbd_msc_sector_read 和 usbd_msc_sector_write 就会在线程中执行。 + +CONFIG_USBDEV_MSC_PRIO +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +MSC 读写线程的优先级,默认是 4,数值越小,优先级越高 + +CONFIG_USBDEV_MSC_STACKSIZE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +MSC 读写线程的堆栈大小,默认 2K 字节 + +CONFIG_USBDEV_RNDIS_RESP_BUFFER_SIZE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +rndis 控制传输最大接收和发送的长度,根据 RNDIS options list 决定最小长度,默认要大于等于 156 + +CONFIG_USBDEV_RNDIS_ETH_MAX_FRAME_SIZE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +rndis 以太网帧的最大长度,默认 1580 + +CONFIG_USBDEV_RNDIS_VENDOR_ID +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +CONFIG_USBDEV_RNDIS_VENDOR_DESC +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +CONFIG_USBDEV_RNDIS_USING_LWIP +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +rndis 与 lwip 接口的对接 + +主机协议栈 CONFIG +--------------------- + +以下参数决定了支持的最大外部hub数量,接口数,每个接口的端点数和 altsetting 数量,更改此值会影响 ram 的大小,建议根据实际情况更改。 + +.. code-block:: C + + #define CONFIG_USBHOST_MAX_RHPORTS 1 + #define CONFIG_USBHOST_MAX_EXTHUBS 1 + #define CONFIG_USBHOST_MAX_EHPORTS 4 + #define CONFIG_USBHOST_MAX_INTERFACES 6 + #define CONFIG_USBHOST_MAX_INTF_ALTSETTINGS 1 + #define CONFIG_USBHOST_MAX_ENDPOINTS 4 + +以下参数决定了支持的 class 数目,更改此值会影响 ram 的大小,建议根据实际情况更改。 + +.. code-block:: C + + #define CONFIG_USBHOST_MAX_SERIAL_CLASS 4 + #define CONFIG_USBHOST_MAX_HID_CLASS 4 + #define CONFIG_USBHOST_MAX_MSC_CLASS 2 + #define CONFIG_USBHOST_MAX_AUDIO_CLASS 1 + #define CONFIG_USBHOST_MAX_VIDEO_CLASS 1 + +CONFIG_USBHOST_PSC_PRIO +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +主机插拔线程的优先级,默认是 0,数值越小,优先级越高 + +CONFIG_USBHOST_PSC_STACKSIZE +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +主机插拔线程的堆栈大小,默认 2K 字节 + +CONFIG_USBHOST_REQUEST_BUFFER_LEN +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +控制传输能够接收或者发送的最大长度 + +CONFIG_USBHOST_CONTROL_TRANSFER_TIMEOUT +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +控制传输发送或者接收的超时时间,默认 500 ms + +CONFIG_USBHOST_MSC_TIMEOUT +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +MSC 读写传输的超时时间,默认 5s \ No newline at end of file diff --git a/docs/zh/api/api_device.rst b/docs/zh/api/api_device.rst new file mode 100644 index 00000000..4c6617b1 --- /dev/null +++ b/docs/zh/api/api_device.rst @@ -0,0 +1,505 @@ +设备协议栈 +========================= + +设备协议栈主要负责枚举和驱动加载,枚举这边就不说了,驱动加载,也就是接口驱动加载,主要是依靠 `usbd_add_interface` 函数,用于记录传入的接口驱动并保存到接口数组表,当主机进行类请求时就可以查找接口表进行访问了。 +在调用 `usbd_desc_register` 以后需要进行接口注册和端点注册,口诀如下: + +- 有多少个接口就调用多少次 `usbd_add_interface`,参数填相关 `xxx_init_intf`, 如果没有支持的,手动创建一个 intf 填入 +- 有多少个端点就调用多少次 `usbd_add_endpoint`,当中断完成时,会调用到注册的端点回调中。 + +参考下面这张图: + +.. figure:: img/api_device1.png + +CORE +----------------- + +端点结构体 +"""""""""""""""""""""""""""""""""""" + +端点结构体主要用于注册不同端点地址的中断完成回调函数。 + +.. code-block:: C + + struct usbd_endpoint { + uint8_t ep_addr; + usbd_endpoint_callback ep_cb; + }; + +- **ep_addr** 端点地址(带方向) +- **ep_cb** 端点完成中断回调函数。 + +.. note:: 总结一句话:in 回调函数等价于 dma 发送完成中断回调函数;out 回调函数等价于 dma 接收完成中断回调函数 + +接口结构体 +"""""""""""""""""""""""""""""""""""" + +接口结构体主要用于注册不同类设备除了标准设备请求外的其他请求,包括类设备请求、厂商设备请求和自定义设备请求。以及协议栈中的相关通知回调函数。 + +.. code-block:: C + + struct usbd_interface { + usbd_request_handler class_interface_handler; + usbd_request_handler class_endpoint_handler; + usbd_request_handler vendor_handler; + usbd_notify_handler notify_handler; + const uint8_t *hid_report_descriptor; + uint32_t hid_report_descriptor_len; + uint8_t intf_num; + }; + +- **class_interface_handler** class setup 请求回调函数,接收者为接口 +- **class_endpoint_handler** class setup 请求回调函数,接收者为端点 +- **vendor_handler** vendor setup 请求回调函数 +- **notify_handler** 中断标志、协议栈相关状态回调函数 +- **hid_report_descriptor** hid 报告描述符 +- **hid_report_descriptor_len** hid 报告描述符长度 +- **intf_num** 当前接口偏移 + +usbd_desc_register +"""""""""""""""""""""""""""""""""""" + +``usbd_desc_register`` 用来注册 USB 描述符,描述符种类包括:设备描述符、配置描述符(包含配置描述符、接口描述符、class 类描述符、端点描述符)、字符串描述符、设备限定描述符,其他速度描述符, +bos描述符,winusb 描述符。 + +.. code-block:: C + + // 开启 CONFIG_USBDEV_ADVANCE_DESC + void usbd_desc_register(uint8_t busid, const struct usb_descriptor *desc); + + // 关闭 CONFIG_USBDEV_ADVANCE_DESC + void usbd_desc_register(uint8_t busid, const uint8_t *desc); + void usbd_msosv1_desc_register(uint8_t busid, struct usb_msosv1_descriptor *desc); + void usbd_msosv2_desc_register(uint8_t busid, struct usb_msosv2_descriptor *desc); + void usbd_bos_desc_register(uint8_t busid, struct usb_bos_descriptor *desc); + void usbd_webusb_desc_register(uint8_t busid, struct usb_webusb_descriptor *desc); + +- **desc** 描述符的句柄 + +.. note:: 当前默认开启 CONFIG_USBDEV_ADVANCE_DESC,如果需要使用旧版本 API 请关闭该宏,从 v1.6.0 开始只有开启了 CONFIG_USBDEV_ADVANCE_DESC 的 API + +usbd_add_interface +"""""""""""""""""""""""""""""""""""" + +``usbd_add_interface`` 添加一个接口驱动。 **添加顺序必须按照描述符中接口顺序**。 + +.. code-block:: C + + void usbd_add_interface(uint8_t busid, struct usbd_interface *intf); + +- **busid** USB 总线 id +- **intf** 接口驱动句柄,通常从不同 class 的 `xxx_init_intf` 函数获取 + +usbd_add_endpoint +"""""""""""""""""""""""""""""""""""" + +``usbd_add_endpoint`` 添加一个端点中断完成回调函数。 + +.. code-block:: C + + void usbd_add_endpoint(uint8_t busid, struct usbd_endpoint *ep); + +- **busid** USB 总线 id +- **ep** 端点句柄 + +usbd_initialize +"""""""""""""""""""""""""""""""""""" + +``usbd_initialize`` 用来初始化 usb device 寄存器配置、usb 时钟、中断等,需要注意,此函数必须在注册描述符 API 最后。 **如果使用 os,必须放在线程中执行**。 + +.. code-block:: C + + int usbd_initialize(uint8_t busid, uintptr_t reg_base, usbd_event_handler_t event_handler); + +- **busid** USB 总线 id +- **reg_base** USB 设备寄存器基地址 +- **event_handler** 协议栈中断或者状态回调函数,event 事件 +- **return** 返回 0 表示成功,其他值表示失败 + +event 事件包括: + +.. code-block:: C + + USBD_EVENT_ERROR, /** USB error reported by the controller */ + USBD_EVENT_RESET, /** USB reset */ + USBD_EVENT_SOF, /** Start of Frame received */ + USBD_EVENT_CONNECTED, /** USB connected*/ + USBD_EVENT_DISCONNECTED, /** USB disconnected */ + USBD_EVENT_SUSPEND, /** USB connection suspended by the HOST */ + USBD_EVENT_RESUME, /** USB connection resumed by the HOST */ + + /* USB DEVICE STATUS */ + USBD_EVENT_CONFIGURED, /** USB configuration done */ + USBD_EVENT_SET_INTERFACE, /** USB interface selected */ + USBD_EVENT_SET_REMOTE_WAKEUP, /** USB set remote wakeup */ + USBD_EVENT_CLR_REMOTE_WAKEUP, /** USB clear remote wakeup */ + USBD_EVENT_INIT, /** USB init done when call usbd_initialize */ + USBD_EVENT_DEINIT, /** USB deinit done when call usbd_deinitialize */ + USBD_EVENT_UNKNOWN + +.. note:: 大部分 IP USBD_EVENT_CONNECTED 和 USBD_EVENT_DISCONNECTED 事件都不支持,当前仅 HPM 芯片支持,其余芯片自行设计vbus检测电路替代 + +usbd_deinitialize +"""""""""""""""""""""""""""""""""""" + +``usbd_deinitialize`` 用来反初始化 usb device,关闭 usb 设备时钟、中断等。 + +.. code-block:: C + + int usbd_deinitialize(uint8_t busid); + +- **busid** USB 总线 id +- **return** 返回 0 表示成功,其他值表示失败 + +CDC ACM +----------------- + +usbd_cdc_acm_init_intf +"""""""""""""""""""""""""""""""""""" + +``usbd_cdc_acm_init_intf`` 用来初始化 USB CDC ACM 类接口,并实现该接口相关的函数。 + +- ``cdc_acm_class_interface_request_handler`` 用来处理 USB CDC ACM 类 Setup 请求。 +- ``cdc_notify_handler`` 用来处理 USB CDC 其他中断回调函数。 + +.. code-block:: C + + struct usbd_interface *usbd_cdc_acm_init_intf(uint8_t busid, struct usbd_interface *intf); + +- **busid** USB 总线 id +- **return** 接口句柄 + +usbd_cdc_acm_set_line_coding +"""""""""""""""""""""""""""""""""""" + +``usbd_cdc_acm_set_line_coding`` 用来对串口进行配置,如果仅使用 USB 而不用 串口,该接口不用用户实现,使用默认。 + +.. code-block:: C + + void usbd_cdc_acm_set_line_coding(uint8_t busid, uint8_t intf, struct cdc_line_coding *line_coding); + +- **busid** USB 总线 id +- **intf** 控制接口号 +- **line_coding** 串口配置 + +usbd_cdc_acm_get_line_coding +"""""""""""""""""""""""""""""""""""" + +``usbd_cdc_acm_get_line_coding`` 用来获取串口进行配置,如果仅使用 USB 而不用 串口,该接口不用用户实现,使用默认。 + +.. code-block:: C + + void usbd_cdc_acm_get_line_coding(uint8_t busid, uint8_t intf, struct cdc_line_coding *line_coding); + +- **busid** USB 总线 id +- **intf** 控制接口号 +- **line_coding** 串口配置 + +usbd_cdc_acm_set_dtr +"""""""""""""""""""""""""""""""""""" + +``usbd_cdc_acm_set_dtr`` 用来控制串口 DTR 。如果仅使用 USB 而不用 串口,该接口不用用户实现,使用默认。 + +.. code-block:: C + + void usbd_cdc_acm_set_dtr(uint8_t busid, uint8_t intf, bool dtr); + +- **busid** USB 总线 id +- **intf** 控制接口号 +- **dtr** dtr 为1表示拉低电平,为0表示拉高电平 + +usbd_cdc_acm_set_rts +"""""""""""""""""""""""""""""""""""" + +``usbd_cdc_acm_set_rts`` 用来控制串口 RTS 。如果仅使用 USB 而不用 串口,该接口不用用户实现,使用默认。 + +.. code-block:: C + + void usbd_cdc_acm_set_rts(uint8_t busid, uint8_t intf, bool rts); + +- **busid** USB 总线 id +- **intf** 控制接口号 +- **rts** rts 为1表示拉低电平,为0表示拉高电平 + +CDC_ACM_DESCRIPTOR_INIT +"""""""""""""""""""""""""""""""""""" + +``CDC_ACM_DESCRIPTOR_INIT`` 配置了默认的 cdc acm 需要的描述符以及参数,方便用户使用。总长度为 `CDC_ACM_DESCRIPTOR_LEN` 。 + +.. code-block:: C + + CDC_ACM_DESCRIPTOR_INIT(bFirstInterface, int_ep, out_ep, in_ep, str_idx); + +- **bFirstInterface** 表示该 cdc acm 第一个接口所在所有接口的偏移 +- **int_ep** 表示中断端点地址(带方向) +- **out_ep** 表示 bulk out 端点地址(带方向) +- **in_ep** 表示 bulk in 端点地址(带方向) +- **str_idx** 控制接口对应的字符串 id + +HID +----------------- + +usbd_hid_init_intf +"""""""""""""""""""""""""""""""""""" + +``usbd_hid_init_intf`` 用来初始化 USB HID 类接口,并实现该接口相关的函数: + +- ``hid_class_interface_request_handler`` 用来处理 USB HID 类的 Setup 请求。 +- ``hid_notify_handler`` 用来处理 USB HID 其他中断回调函数。 + +.. code-block:: C + + struct usbd_interface *usbd_hid_init_intf(uint8_t busid, struct usbd_interface *intf, const uint8_t *desc, uint32_t desc_len); + +- **busid** USB 总线 id +- **desc** 报告描述符 +- **desc_len** 报告描述符长度 + +MSC +----------------- + +usbd_msc_init_intf +"""""""""""""""""""""""""""""""""""" + +``usbd_msc_init_intf`` 用来初始化 MSC 类接口,并实现该接口相关函数,并且注册端点回调函数。(因为 msc bot 协议是固定的,所以不需要用于实现,因此端点回调函数自然不需要用户实现)。 + +- ``msc_storage_class_interface_request_handler`` 用于处理 USB MSC Setup 中断请求。 +- ``msc_storage_notify_handler`` 用于实现 USB MSC 其他中断回调函数。 + +- ``mass_storage_bulk_out`` 用于处理 USB MSC 端点 out 中断。 +- ``mass_storage_bulk_in`` 用于处理 USB MSC 端点 in 中断。 + +.. code-block:: C + + struct usbd_interface *usbd_msc_init_intf(uint8_t busid, struct usbd_interface *intf, const uint8_t out_ep, const uint8_t in_ep); + +- **busid** USB 总线 id +- **out_ep** out 端点地址 +- **in_ep** in 端点地址 + +usbd_msc_get_cap +"""""""""""""""""""""""""""""""""""" + +``usbd_msc_get_cap`` 用来获取存储器的 lun、扇区个数和每个扇区大小。用户必须实现该函数。 + +.. code-block:: C + + void usbd_msc_get_cap(uint8_t busid, uint8_t lun, uint32_t *block_num, uint16_t *block_size); + +- **busid** USB 总线 id +- **lun** 存储逻辑单元,暂时无用,默认支持一个 +- **block_num** 存储扇区个数 +- **block_size** 存储扇区大小 + +usbd_msc_sector_read +"""""""""""""""""""""""""""""""""""" + +``usbd_msc_sector_read`` 用来对存储器某个扇区开始的地址进行数据读取。用户必须实现该函数。 + +.. code-block:: C + + int usbd_msc_sector_read(uint8_t busid, uint8_t lun, uint32_t sector, uint8_t *buffer, uint32_t length); + +- **busid** USB 总线 id +- **lun** 存储逻辑单元,暂时无用,默认支持一个 +- **sector** 扇区偏移 +- **buffer** 存储读取的数据的指针 +- **length** 读取长度 + + +usbd_msc_sector_write +"""""""""""""""""""""""""""""""""""" + +``usbd_msc_sector_write`` 用来对存储器某个扇区开始写入数据。用户必须实现该函数。 + +.. code-block:: C + + int usbd_msc_sector_write(uint8_t busid, uint8_t lun, uint32_t sector, uint8_t *buffer, uint32_t length); + +- **busid** USB 总线 id +- **lun** 存储逻辑单元,暂时无用,默认支持一个 +- **sector** 扇区偏移 +- **buffer** 写入数据指针 +- **length** 写入长度 + +UAC +----------------- + +usbd_audio_init_intf +"""""""""""""""""""""""""""""""""""" + +``usbd_audio_init_intf`` 用来初始化 USB Audio 类接口,并实现该接口相关的函数: + +- ``audio_class_interface_request_handler`` 用于处理 USB Audio Setup 接口接收者中断请求。 +- ``audio_class_endpoint_request_handler`` 用于处理 USB Audio Setup 端点接收者中断请求。 +- ``audio_notify_handler`` 用于实现 USB Audio 其他中断回调函数。 + +.. code-block:: C + + struct usbd_interface *usbd_audio_init_intf(uint8_t busid, struct usbd_interface *intf, + uint16_t uac_version, + struct audio_entity_info *table, + uint8_t num); + +- **busid** USB 总线 id +- **intf** 接口句柄 +- **uac_version** 音频类版本,UAC1.0 或 UAC2.0 +- **table** 音频实体信息表 +- **num** 音频实体信息表长度 + +usbd_audio_open +"""""""""""""""""""""""""""""""""""" + +``usbd_audio_open`` 用来开启音频数据传输。主机发送开启命令的回调函数。 + +.. code-block:: C + + void usbd_audio_open(uint8_t intf); + +- **intf** 开启的接口号 + +usbd_audio_close +"""""""""""""""""""""""""""""""""""" + +``usbd_audio_close`` 用来关闭音频数据传输。主机发送关闭命令的回调函数。 + +.. code-block:: C + + void usbd_audio_close(uint8_t intf); + +- **intf** 关闭的接口号 + +usbd_audio_set_mute +"""""""""""""""""""""""""""""""""""" + +``usbd_audio_set_mute`` 用来设置静音。 + +.. code-block:: C + + void usbd_audio_set_mute(uint8_t busid, uint8_t ep, uint8_t ch, bool mute); + +- **busid** USB 总线 id +- **ep** 要设置静音的端点 +- **ch** 要设置静音的通道 +- **mute** 为1 表示静音,0相反 + +usbd_audio_set_volume +"""""""""""""""""""""""""""""""""""" + +``usbd_audio_set_volume`` 用来设置音量。 + +.. code-block:: C + + void usbd_audio_set_volume(uint8_t busid, uint8_t ep, uint8_t ch, int volume_db); + +- **busid** USB 总线 id +- **ep** 要设置音量的端点 +- **ch** 要设置音量的通道 +- **volume_db** 要设置音量的分贝,单位 -100dB ~ 0dB + +usbd_audio_set_sampling_freq +"""""""""""""""""""""""""""""""""""" + +``usbd_audio_set_sampling_freq`` 用来设置设备上音频模块的采样率 + +.. code-block:: C + + void usbd_audio_set_sampling_freq(uint8_t busid, uint8_t ep, uint32_t sampling_freq); + +- **ep** 要设置采样率的端点 +- **sampling_freq** 要设置的采样率 + +usbd_audio_get_sampling_freq_table +"""""""""""""""""""""""""""""""""""" + +``usbd_audio_get_sampling_freq_table`` 用来获取支持的采样率列表,如果函数没有实现,则使用默认采样率列表。 UAC2 only。 + +.. code-block:: C + + void usbd_audio_get_sampling_freq_table(uint8_t busid, uint8_t ep, uint8_t **sampling_freq_table); + +- **ep** 要获取采样率的端点 +- **sampling_freq_table** 采样率列表地址,格式参考默认采样率列表 + +UVC +----------------- + +usbd_video_init_intf +"""""""""""""""""""""""""""""""""""" + +``usbd_video_init_intf`` 用来初始化 USB Video 类接口,并实现该接口相关的函数: + +- ``video_class_interface_request_handler`` 用于处理 USB Video Setup 中断请求。 +- ``video_notify_handler`` 用于实现 USB Video 其他中断回调函数。 + +.. code-block:: C + + struct usbd_interface *usbd_video_init_intf(uint8_t busid, struct usbd_interface *intf, + uint32_t dwFrameInterval, + uint32_t dwMaxVideoFrameSize, + uint32_t dwMaxPayloadTransferSize); +- **busid** USB 总线 id +- **intf** 接口句柄 +- **dwFrameInterval** 视频帧间隔,单位 100ns +- **dwMaxVideoFrameSize** 最大视频帧大小 +- **dwMaxPayloadTransferSize** 最大负载传输大小 + +usbd_video_open +"""""""""""""""""""""""""""""""""""" + +``usbd_video_open`` 用来开启视频数据传输。 + +.. code-block:: C + + void usbd_video_open(uint8_t intf); + +- **intf** 开启的接口号 + +usbd_video_close +"""""""""""""""""""""""""""""""""""" + +``usbd_video_close`` 用来关闭视频数据传输。 + +.. code-block:: C + + void usbd_video_open(uint8_t intf); + +- **intf** 关闭的接口号 + +usbd_video_stream_start_write +"""""""""""""""""""""""""""""""""""" + +``usbd_video_stream_start_write`` 用来启动一帧视频数据流发送。需要搭配 `usbd_video_stream_split_transfer` 使用。 + +.. code-block:: C + + int usbd_video_stream_start_write(uint8_t busid, uint8_t ep, uint8_t *ep_buf, uint8_t *stream_buf, uint32_t stream_len, bool do_copy); + +- **busid** USB 总线 id +- **ep** 视频数据端点地址 +- **ep_buf** 视频数据端点传输缓冲区 +- **stream_buf** 一帧视频数据源缓冲区 +- **stream_len** 一帧视频数据源缓冲区大小 +- **do_copy** 是否需要将 stream_buf 数据复制到 ep_buf 中,当前仅当 stream_buf 在 nocache 区域并且未开启 DCACHE_ENABLE 时该参数才为 false + +usbd_video_stream_split_transfer +"""""""""""""""""""""""""""""""""""" + +``usbd_video_stream_split_transfer`` 用来分割视频数据流发送。需要搭配 `usbd_video_stream_start_write` 使用。 + +.. code-block:: C + + int usbd_video_stream_split_transfer(uint8_t busid, uint8_t ep); + +- **busid** USB 总线 id +- **ep** 视频数据端点地址 +- **return** 返回 true 表示一帧数据发送完成,false 表示数据未发送完成 + +RNDIS +----------------- + +CDC ECM +----------------- + +MTP +----------------- diff --git a/docs/zh/api/api_host.rst b/docs/zh/api/api_host.rst new file mode 100644 index 00000000..46d1e428 --- /dev/null +++ b/docs/zh/api/api_host.rst @@ -0,0 +1,317 @@ +主机协议栈 +========================= + +关于主机协议栈中结构体的命名、分类、成员组成,参考下面这两张图: + +.. figure:: img/api_host1.png +.. figure:: img/api_host2.png + +CORE +----------------- + +CLASS 驱动信息结构体 +"""""""""""""""""""""""""""""""""""" + +.. code-block:: C + + struct usbh_class_info { + uint8_t match_flags; /* Used for product specific matches; range is inclusive */ + uint8_t bInterfaceClass; /* Base device class code */ + uint8_t bInterfaceSubClass; /* Sub-class, depends on base class. Eg. */ + uint8_t bInterfaceProtocol; /* Protocol, depends on base class. Eg. */ + const uint16_t (*id_table)[2]; /* List of Vendor/Product ID pairs */ + const struct usbh_class_driver *class_driver; + }; + +端点结构体 +"""""""""""""""""""""""""""""""""""" + +.. code-block:: C + + struct usbh_endpoint { + struct usb_endpoint_descriptor ep_desc; + }; + +接口备用结构体 +"""""""""""""""""""""""""""""""""""" + +.. code-block:: C + + struct usbh_interface_altsetting { + struct usb_interface_descriptor intf_desc; + struct usbh_endpoint ep[CONFIG_USBHOST_MAX_ENDPOINTS]; + }; + +接口结构体 +"""""""""""""""""""""""""""""""""""" + +.. code-block:: C + + struct usbh_interface { + char devname[CONFIG_USBHOST_DEV_NAMELEN]; + struct usbh_class_driver *class_driver; + void *priv; + struct usbh_interface_altsetting altsetting[CONFIG_USBHOST_MAX_INTF_ALTSETTINGS]; + uint8_t altsetting_num; + }; + +配置结构体 +"""""""""""""""""""""""""""""""""""" + +.. code-block:: C + + struct usbh_configuration { + struct usb_configuration_descriptor config_desc; + struct usbh_interface intf[CONFIG_USBHOST_MAX_INTERFACES]; + }; + +hubport 结构体 +"""""""""""""""""""""""""""""""""""" + +.. code-block:: C + + struct usbh_hubport { + bool connected; /* True: device connected; false: disconnected */ + uint8_t port; /* Hub port index */ + uint8_t dev_addr; /* device address */ + uint8_t speed; /* device speed */ + uint8_t depth; /* distance from root hub */ + uint8_t route; /* route string */ + uint8_t slot_id; /* slot id */ + struct usb_device_descriptor device_desc; + struct usbh_configuration config; + const char *iManufacturer; + const char *iProduct; + const char *iSerialNumber; + uint8_t *raw_config_desc; + struct usb_setup_packet *setup; + struct usbh_hub *parent; + struct usbh_hub *self; /* if this hubport is a hub */ + struct usbh_bus *bus; + struct usb_endpoint_descriptor ep0; + struct usbh_urb ep0_urb; + usb_osal_mutex_t mutex; + }; + +hub 结构体 +"""""""""""""""""""""""""""""""""""" + +.. code-block:: C + + struct usbh_hub { + bool connected; + bool is_roothub; + uint8_t index; + uint8_t hub_addr; + uint8_t speed; + uint8_t nports; + uint8_t powerdelay; + uint8_t tt_think; + bool ismtt; + struct usb_hub_descriptor hub_desc; /* USB 2.0 only */ + struct usb_hub_ss_descriptor hub_ss_desc; /* USB 3.0 only */ + struct usbh_hubport child[CONFIG_USBHOST_MAX_EHPORTS]; + struct usbh_hubport *parent; + struct usbh_bus *bus; + struct usb_endpoint_descriptor *intin; + struct usbh_urb intin_urb; + uint8_t *int_buffer; + struct usb_osal_timer *int_timer; + }; + +usbh_initialize +"""""""""""""""""""""""""""""""""""" + +``usbh_initialize`` 用来初始化 usb 主机协议栈,包括:初始化 usb 主机控制器,创建 roothub 设备,创建 hub 检测线程。 + +.. code-block:: C + + int usbh_initialize(uint8_t busid, uint32_t reg_base, usbh_event_handler_t event_handler); + +- **busid** bus id,从 0开始,不能超过 `CONFIG_USBHOST_MAX_BUS` +- **reg_base** hcd 寄存器基地址 +- **event_handler** host 事件回调函数,可以为NULL +- **return** 0 表示正常其他表示错误 + +usbh_find_class_instance +"""""""""""""""""""""""""""""""""""" + +``usbh_find_class_instance`` 根据注册的 class 名称查找对应的 class 结构体句柄。 + +.. code-block:: C + + void *usbh_find_class_instance(const char *devname); + +- **devname** class 名称 +- **return** class 结构体句柄 + +lsusb +"""""""""""""""""""""""""""""""""""" + +``lsusb`` 用来查看和操作 hub 上的设备信息。需要借助 shell 插件使用。 + +.. code-block:: C + + int lsusb(int argc, char **argv); + +SERIAL +----------------- + +usbh_serial_open +"""""""""""""""""""""""""""""""""""" + +``usbh_serial_open`` 根据路径打开一个串口设备。 + +.. code-block:: C + + struct usbh_serial *usbh_serial_open(const char *devname, uint32_t open_flags); + +- **devname** 串口路径 +- **open_flags** 打开标志,参考 `USBH_SERIAL_OFLAG_*` 定义 +- **return** serial 结构体句柄 + +usbh_serial_close +"""""""""""""""""""""""""""""""""""" + +``usbh_serial_close`` 关闭串口设备。 + +.. code-block:: C + + void usbh_serial_close(struct usbh_serial *serial); + +- **serial** serial 结构体句柄 + +usbh_serial_control +"""""""""""""""""""""""""""""""""""" + +``usbh_serial_control`` 对串口进行配置。 + +.. code-block:: C + + int usbh_serial_control(struct usbh_serial *serial, int cmd, void *arg); + +- **serial** serial 结构体句柄 +- **cmd** 控制命令,参考 `USBH_SERIAL_CMD_*` 定义 +- **arg** 控制参数指针 +- **return** 0 表示正常其他表示错误 + +usbh_serial_write +"""""""""""""""""""""""""""""""""""" + +``usbh_serial_write`` 向串口写数据。 + +.. code-block:: C + + int usbh_serial_write(struct usbh_serial *serial, const void *buffer, uint32_t buflen); + +- **serial** serial 结构体句柄 +- **buffer** 数据缓冲区指针 +- **buflen** 要写入的数据长度 +- **return** 实际写入的数据长度或者错误码 + +.. note:: 如果没有开启 CONFIG_USB_DCACHE_ENABLE,则 buffer 需要是 nocache区域,否则需要是对齐到 CONFIG_USB_ALIGN_SIZE 的区域。 + +usbh_serial_read +"""""""""""""""""""""""""""""""""""" + +``usbh_serial_read`` 从串口读数据。 **如果没有设置波特率,不允许使用该 API,设置波特率后,内部会开启 rx 接收并将数据写入 ringbuf **。 + +.. code-block:: C + + int usbh_serial_read(struct usbh_serial *serial, void *buffer, uint32_t buflen); + +- **serial** serial 结构体句柄 +- **buffer** 数据缓冲区指针 +- **buflen** 要读取的最大数据长度 +- **return** 实际读取的数据长度或者错误码 + +.. note:: 由于内部使用了 ringbuffer,对于用户的 buffer 属性没有限制。 + +usbh_serial_cdc_write_async +"""""""""""""""""""""""""""""""""""" + +``usbh_serial_cdc_write_async`` 异步从串口读数据。 **如果设置了波特率,不允许使用该 API**。 + +.. code-block:: C + + int usbh_serial_cdc_write_async(struct usbh_serial *serial, uint8_t *buffer, uint32_t buflen, usbh_complete_callback_t complete, void *arg); + +- **serial** serial 结构体句柄 +- **buffer** 数据缓冲区指针 +- **buflen** 要发送的数据长度 +- **complete** 读数据完成回调函数 +- **arg** 回调函数参数 +- **return** 0 表示正常其他表示错误 + +.. note:: 如果没有开启 CONFIG_USB_DCACHE_ENABLE,则 buffer 需要是 nocache区域,否则需要是对齐到 CONFIG_USB_ALIGN_SIZE 的区域。 + +usbh_serial_cdc_read_async +"""""""""""""""""""""""""""""""""""" + +``usbh_serial_cdc_read_async`` 异步从串口读数据。 **如果设置了波特率,不允许使用该 API,设置波特率后,内部会开启 rx 接收并将数据写入 ringbuf **。 + +.. code-block:: C + + int usbh_serial_cdc_read_async(struct usbh_serial *serial, uint8_t *buffer, uint32_t buflen, usbh_complete_callback_t complete, void *arg); + +- **serial** serial 结构体句柄 +- **buffer** 数据缓冲区指针 +- **buflen** 要读取的最大数据长度,一次最高 16K。并且需要是 wMaxPacketSize 的整数倍 +- **complete** 读数据完成回调函数 +- **arg** 回调函数参数 +- **return** 0 表示正常其他表示错误 + +.. note:: 如果没有开启 CONFIG_USB_DCACHE_ENABLE,则 buffer 需要是 nocache区域,否则需要是对齐到 CONFIG_USB_ALIGN_SIZE 的区域。 + +HID +----------------- + +MSC +----------------- + +usbh_msc_scsi_init +"""""""""""""""""""""""""""""""""""" + +``usbh_msc_scsi_init`` 初始化 msc scsi 设备。获取 MSC 状态和容量信息。 + +.. code-block:: C + + int usbh_msc_scsi_init(struct usbh_msc *msc_class); + +- **msc_class** msc 结构体句柄 +- **return** 0 表示正常其他表示错误 + +usbh_msc_scsi_write10 +"""""""""""""""""""""""""""""""""""" + +``usbh_msc_scsi_write10`` 向 msc 设备写数据。 + +.. code-block:: C + + int usbh_msc_scsi_write10(struct usbh_msc *msc_class, uint32_t start_sector, const uint8_t *buffer, uint32_t nsectors); + +- **msc_class** msc 结构体句柄 +- **start_sector** 起始扇区 +- **buffer** 数据缓冲区指针 +- **nsectors** 要写入的扇区数 +- **return** 返回 0 表示正常其他表示错误 + +usbh_msc_scsi_read10 +"""""""""""""""""""""""""""""""""""" + +``usbh_msc_scsi_read10`` 从 msc 设备读数据。 + +.. code-block:: C + + int usbh_msc_scsi_read10(struct usbh_msc *msc_class, uint32_t start_sector, uint8_t *buffer, uint32_t nsectors); + +- **msc_class** msc 结构体句柄 +- **start_sector** 起始扇区 +- **buffer** 数据缓冲区指针 +- **nsectors** 要读取的扇区数 +- **return** 返回 0 表示正常其他表示错误 + +NETWORK +----------------- + +已对接 lwIP 协议栈或者其他网络协议栈,使用 socket API 即可。 \ No newline at end of file diff --git a/docs/zh/api/api_port.rst b/docs/zh/api/api_port.rst new file mode 100644 index 00000000..c214daa7 --- /dev/null +++ b/docs/zh/api/api_port.rst @@ -0,0 +1,266 @@ +主从驱动 +========================= + +.. note:: 请注意,v1.1 版本开始增加 busid 形参,其余保持不变,所以 API 说明不做更新 + +device controller(dcd) +------------------------- + +usb_dc_init +"""""""""""""""""""""""""""""""""""" + +``usb_dc_init`` 用于初始化 usb device controller 寄存器,设置 usb 引脚、时钟、中断等等。 **此函数不对用户开放**。 + +.. code-block:: C + + int usb_dc_init(void); + +- **return** 返回 0 表示正确,其他表示错误 + +usb_dc_deinit +"""""""""""""""""""""""""""""""""""" + +``usb_dc_deinit`` 用于反初始化 usb device controller 寄存器。 **此函数不对用户开放**。 + +.. code-block:: C + + int usb_dc_deinit(void); + +- **return** 返回 0 表示正确,其他表示错误 + +usbd_set_address +"""""""""""""""""""""""""""""""""""" + +``usbd_set_address`` 设置设备地址。 **此函数不对用户开放**。 + +.. code-block:: C + + int usbd_set_address(const uint8_t addr); + +- **addr** 设备地址 +- **return** 返回 0 表示正确,其他表示错误 + +usbd_ep_open +"""""""""""""""""""""""""""""""""""" + +``usbd_ep_open`` 设置端点的属性,开启对应端点的中断。 **此函数不对用户开放**。 + +.. code-block:: C + + int usbd_ep_open(const struct usb_endpoint_descriptor *ep); + +- **ep** 端点描述符 +- **return** 返回 0 表示正确,其他表示错误 + +usbd_ep_close +"""""""""""""""""""""""""""""""""""" + +``usbd_ep_close`` 关闭端点。 **此函数不对用户开放**。 + +.. code-block:: C + + int usbd_ep_close(const uint8_t ep); + +- **ep** 端点地址 +- **return** 返回 0 表示正确,其他表示错误 + +usbd_ep_set_stall +"""""""""""""""""""""""""""""""""""" + +``usbd_ep_set_stall`` 将端点设置成 stall 状态并发送 stall 握手包。 **此函数对用户开放**。 + +.. code-block:: C + + int usbd_ep_set_stall(const uint8_t ep); + +- **ep** 端点地址 +- **return** 返回 0 表示正确,其他表示错误 + +usbd_ep_clear_stall +"""""""""""""""""""""""""""""""""""" + +``usbd_ep_clear_stall`` 清除端点的 stall 状态。 **此函数不对用户开放**。 + +.. code-block:: C + + int usbd_ep_clear_stall(const uint8_t ep); + +- **ep** 端点地址 +- **return** 返回 0 表示正确,其他表示错误 + +usbd_ep_is_stalled +"""""""""""""""""""""""""""""""""""" + +``usbd_ep_is_stalled`` 读取当前端点的 stall 状态。 **此函数不对用户开放**。 + +.. code-block:: C + + int usbd_ep_is_stalled(const uint8_t ep, uint8_t *stalled); + +- **ep** 端点地址 +- **return** 返回 1 表示 stalled,0 表示没有 stall + +usbd_ep_start_write +"""""""""""""""""""""""""""""""""""" + +``usbd_ep_start_write`` 启动端点发送,发送完成以后,会调用注册的 in 端点传输完成中断回调函数。该函数为异步发送。 **此函数对用户开放**。 + +.. code-block:: C + + int usbd_ep_start_write(const uint8_t ep, const uint8_t *data, uint32_t data_len); + +- **ep** in 端点地址 +- **data** 发送数据缓冲区 +- **data_len** 发送长度,原则上无限长,推荐 16K 字节以内 +- **return** 返回 0 表示正确,其他表示错误 + +usbd_ep_start_read +"""""""""""""""""""""""""""""""""""" + +``usbd_ep_start_read`` 启动端点接收,接收完成以后,会调用注册的 out 端点传输完成中断回调函数。该函数为异步接收。 **此函数对用户开放**。 + +.. code-block:: C + + int usbd_ep_start_read(const uint8_t ep, uint8_t *data, uint32_t data_len); + +- **ep** out 端点地址 +- **data** 接收数据缓冲区 +- **data_len** 接收长度,原则上无限长,推荐 16K 字节以内,并且推荐是最大包长的整数倍 +- **return** 返回 0 表示正确,其他表示错误 + +.. note:: 启动接收以后,以下两种情况,会进入传输完成中断:1、最后一包为短包(小于 EP MPS);2、接收总长度等于 data_len + +.. note:: 对于 bulk 传输,data_len 通常设计为 EP MPS,以下三种情况可以修改为多个 EP MPS: 固定长度;自定义协议并携带长度(MSC); 主机手动发送 ZLP 或者短包(RNDIS) + +host controller(hcd) +------------------------ + +usb_hc_init +"""""""""""""""""""""""""""""""""""" + +``usb_hc_init`` 用于初始化 usb host controller 寄存器,设置 usb 引脚、时钟、中断等等。 **此函数不对用户开放**。 + +.. code-block:: C + + int usb_hc_init(void); + +- **return** 返回 0 表示正确,其他表示错误 + +usb_hc_deinit +"""""""""""""""""""""""""""""""""""" + +``usb_hc_deinit`` 用于反初始化 usb host controller 寄存器。 **此函数不对用户开放**。 + +.. code-block:: C + + int usb_hc_deinit(void); + +- **return** 返回 0 表示正确,其他表示错误 + +usbh_roothub_control +"""""""""""""""""""""""""""""""""""" + +``usbh_roothub_control`` 用来对 roothub 发起请求, **此函数不对用户开放**。 + +.. code-block:: C + + int usbh_roothub_control(struct usb_setup_packet *setup, uint8_t *buf); + +- **setup** 请求 +- **buf** 接收缓冲区 +- **return** 返回 0 表示正确,其他表示错误 + +usbh_submit_urb +"""""""""""""""""""""""""""""""""""" + +``usbh_submit_urb`` 对某个地址上的端点进行数据请求。 **此函数对用户开放**。 + +.. code-block:: C + + int usbh_submit_urb(struct usbh_urb *urb); + +- **urb** usb 请求块 +- **return** 返回 0 表示正确,其他表示错误 + +其中, `urb` 结构体信息如下: + +.. code-block:: C + + struct usbh_urb { + usb_slist_t list; + void *hcpriv; + struct usbh_hubport *hport; + struct usb_endpoint_descriptor *ep; + uint8_t data_toggle; + uint8_t interval; + struct usb_setup_packet *setup; + uint8_t *transfer_buffer; + uint32_t transfer_buffer_length; + int transfer_flags; + uint32_t actual_length; + uint32_t timeout; + int errorcode; + uint32_t num_of_iso_packets; + uint32_t start_frame; + usbh_complete_callback_t complete; + void *arg; + #if defined(__ICCARM__) || defined(__ICCRISCV__) || defined(__ICCRX__) + struct usbh_iso_frame_packet *iso_packet; + #else + struct usbh_iso_frame_packet iso_packet[0]; + #endif + }; + +- **hcpriv** 主机控制器驱动私有成员 +- **hport** 当前 urb 使用的 hport +- **ep** 当前 urb 使用的 ep +- **data_toggle** 当前 data toggle +- **interval** urb 传输间隔,单位 us,如果 interval 大于 1000us,则需要使用软件定时器来维护 +- **setup** setup 请求缓冲区,端点0使用 +- **transfer_buffer** 传输的数据缓冲区 +- **transfer_buffer_length** 传输长度 +- **transfer_flags** 传输时携带的 flag +- **actual_length** 实际传输长度 +- **timeout** 传输超时时间,为 0 该函数则为非阻塞,可在中断中使用 +- **errorcode** 错误码 +- **num_of_iso_packets** iso 帧或者微帧个数 +- **complete** 传输完成回调函数 +- **arg** 传输完成时携带的参数 +- **iso_packet** iso 数据包 + +.. note:: timeout 如何没有特别对时间的要求,必须设置成 0xffffffff,原则上不允许超时,如果超时了,一般不能再继续工作 + +`errorcode` 可以返回以下值: + +.. code-block:: C + + #define USB_ERR_NOMEM 1 + #define USB_ERR_INVAL 2 + #define USB_ERR_NODEV 3 + #define USB_ERR_NOTCONN 4 + #define USB_ERR_NOTSUPP 5 + #define USB_ERR_BUSY 6 + #define USB_ERR_RANGE 7 + #define USB_ERR_STALL 8 + #define USB_ERR_BABBLE 9 + #define USB_ERR_NAK 10 + #define USB_ERR_DT 11 + #define USB_ERR_IO 12 + #define USB_ERR_SHUTDOWN 13 + #define USB_ERR_TIMEOUT 14 + +其中 `iso_packet` 结构体信息如下: + +.. code-block:: C + + struct usbh_iso_frame_packet { + uint8_t *transfer_buffer; + uint32_t transfer_buffer_length; + uint32_t actual_length; + int errorcode; + }; + +- **transfer_buffer** 传输的数据缓冲区 +- **transfer_buffer_length** 传输长度 +- **actual_length** 实际传输长度 +- **errorcode** 错误码 \ No newline at end of file diff --git a/docs/zh/api/img/api_device1.png b/docs/zh/api/img/api_device1.png new file mode 100644 index 00000000..ba218b65 Binary files /dev/null and b/docs/zh/api/img/api_device1.png differ diff --git a/docs/zh/api/img/api_host1.png b/docs/zh/api/img/api_host1.png new file mode 100644 index 00000000..82932f50 Binary files /dev/null and b/docs/zh/api/img/api_host1.png differ diff --git a/docs/zh/api/img/api_host2.png b/docs/zh/api/img/api_host2.png new file mode 100644 index 00000000..7f6d60b8 Binary files /dev/null and b/docs/zh/api/img/api_host2.png differ diff --git a/docs/zh/class/class_audio.rst b/docs/zh/class/class_audio.rst new file mode 100644 index 00000000..d1a9e207 --- /dev/null +++ b/docs/zh/class/class_audio.rst @@ -0,0 +1,4 @@ +UAC +========================= + +参考官方 audio 相关 pdf \ No newline at end of file diff --git a/docs/zh/class/class_cdc.rst b/docs/zh/class/class_cdc.rst new file mode 100644 index 00000000..d3ed560f --- /dev/null +++ b/docs/zh/class/class_cdc.rst @@ -0,0 +1,4 @@ +CDC +========================= + +参考官方 cdc 相关 pdf \ No newline at end of file diff --git a/docs/zh/class/class_hid.rst b/docs/zh/class/class_hid.rst new file mode 100644 index 00000000..0f9ef13d --- /dev/null +++ b/docs/zh/class/class_hid.rst @@ -0,0 +1,4 @@ +HID +========================= + +参考官方 hid 相关 pdf \ No newline at end of file diff --git a/docs/zh/class/class_msc.rst b/docs/zh/class/class_msc.rst new file mode 100644 index 00000000..c01a359c --- /dev/null +++ b/docs/zh/class/class_msc.rst @@ -0,0 +1,4 @@ +MSC +========================= + +参考官方 msc 相关 pdf \ No newline at end of file diff --git a/docs/zh/class/class_video.rst b/docs/zh/class/class_video.rst new file mode 100644 index 00000000..cabe5173 --- /dev/null +++ b/docs/zh/class/class_video.rst @@ -0,0 +1,4 @@ +UVC +========================= + +参考官方 video 相关 pdf \ No newline at end of file diff --git a/docs/zh/class/winusb.rst b/docs/zh/class/winusb.rst new file mode 100644 index 00000000..8c74d3b7 --- /dev/null +++ b/docs/zh/class/winusb.rst @@ -0,0 +1,2 @@ +WINUSB +========================= diff --git a/docs/zh/conf.py b/docs/zh/conf.py new file mode 100644 index 00000000..22427158 --- /dev/null +++ b/docs/zh/conf.py @@ -0,0 +1,37 @@ +# Configuration file for the Sphinx documentation builder. + +# -- Project information + +project = 'CherryUSB' +copyright = '2022 ~ 2026, sakumisu' +author = 'sakumisu' + +release = '1.6.0' +version = '1.6.0' + +# -- General configuration + +extensions = [ + 'sphinx.ext.duration', + 'sphinx.ext.doctest', + 'sphinx.ext.autodoc', + 'sphinx.ext.autosummary', + 'sphinx.ext.intersphinx', + 'recommonmark', + 'sphinx_markdown_tables' +] + +intersphinx_mapping = { +# 'python': ('https://docs.python.org/3/', None), +# 'sphinx': ('https://www.sphinx-doc.org/en/master/', None), +} +intersphinx_disabled_domains = ['std'] + +templates_path = ['_templates'] + +# -- Options for HTML output + +html_theme = 'sphinx_rtd_theme' + +# -- Options for EPUB output +epub_show_urls = 'footnote' diff --git a/docs/zh/demo/img/cherryadb.png b/docs/zh/demo/img/cherryadb.png new file mode 100644 index 00000000..512586b9 Binary files /dev/null and b/docs/zh/demo/img/cherryadb.png differ diff --git a/docs/zh/demo/img/otg.png b/docs/zh/demo/img/otg.png new file mode 100644 index 00000000..9605176a Binary files /dev/null and b/docs/zh/demo/img/otg.png differ diff --git a/docs/zh/demo/img/rtt_adb_shell1.png b/docs/zh/demo/img/rtt_adb_shell1.png new file mode 100644 index 00000000..df4964a2 Binary files /dev/null and b/docs/zh/demo/img/rtt_adb_shell1.png differ diff --git a/docs/zh/demo/img/rtt_adb_shell2.png b/docs/zh/demo/img/rtt_adb_shell2.png new file mode 100644 index 00000000..88d99a6a Binary files /dev/null and b/docs/zh/demo/img/rtt_adb_shell2.png differ diff --git a/docs/zh/demo/img/usbh_serial.png b/docs/zh/demo/img/usbh_serial.png new file mode 100644 index 00000000..da929c4a Binary files /dev/null and b/docs/zh/demo/img/usbh_serial.png differ diff --git a/docs/zh/demo/usb_otg.rst b/docs/zh/demo/usb_otg.rst new file mode 100644 index 00000000..5cb371c6 --- /dev/null +++ b/docs/zh/demo/usb_otg.rst @@ -0,0 +1,15 @@ +USB OTG +================= + +如果需要使用 OTG 功能,首先使用的芯片需要支持 ID 检测功能,然后使能 ``CONFIG_USB_OTG_ENABLE`` 宏,将之前的例程中 ``usbh_initialize`` 或者 ``usbh_initialize`` +替换成 ``usbotg_initialize`` 即可。 + +ID 检测电路根据不同的 USB 接口类型有所不同,常见的有 micro-USB 和 USB-C 两种接口类型。 + +- 如果是 micro-USB 接口,则将 ID 线连接到芯片的 ID 引脚,并使能 ID 功能即可。 +- 如果是 USB-C 接口,由于没有 ID 引脚,则需要借助 CC 电路转换成 ID 然后连接到芯片的 ID 引脚,常见电路图如下所示(DNP 表示不焊接): + +.. figure:: img/otg.png + + +.. note:: 除 ID 引脚以外,还需要增加 VBUS 输出开关控制,当工作在 host 时,开启 VBUS 供电,当工作在 device 时,关闭 VBUS 供电。 \ No newline at end of file diff --git a/docs/zh/demo/usbd_adb.rst b/docs/zh/demo/usbd_adb.rst new file mode 100644 index 00000000..6855135d --- /dev/null +++ b/docs/zh/demo/usbd_adb.rst @@ -0,0 +1,28 @@ +ADB Device +================= + +adb device demo 参考 `demo/adb/usbd_adb_template.c` 模板。默认适配 **cherrysh** (`platform/demo/adb/cherrysh_port.c`) 和 **rt-thread msh** (`platform/rtthread/usbd_adb_shell.c`),只需要在 main 中添加以下初始化即可。 + +.. code-block:: C + + cherryadb_init(0, xxxxx); + +如果使用 rt-thread,还需要在 menuconfig 中使能 adb device。 + +.. figure:: img/rtt_adb_shell1.png + +进入 adb +-------------- + +- 使用 **cherrysh** 时枚举完成以后自动进入 adb 模式 +- 使用 **msh** 需要在 **msh** 中输入 ``adb_enter`` 进入 adb 模式 + +退出 adb +-------------- + +- 使用 **cherrysh** 时输入 ``exit`` 退出 adb 模式 +- 使用 **msh** 需要在 **msh** 中输入 ``adb_exit`` 退出 adb 模式 + +.. figure:: img/cherryadb.png + +.. figure:: img/rtt_adb_shell2.png diff --git a/docs/zh/demo/usbd_audiov1.rst b/docs/zh/demo/usbd_audiov1.rst new file mode 100644 index 00000000..875db6a0 --- /dev/null +++ b/docs/zh/demo/usbd_audiov1.rst @@ -0,0 +1,10 @@ +AudioV1 Device +================= + +UAC1 demo 参考 `demo/audio_v1_*.c` 模板。 + +在使用 UAC1.0 时,需要注意以下几点: + +- 在使用windows 时,当修改描述符任意参数时,必须同步修改字符串描述符,并且卸载驱动,否则windows会认为设备未更改,继续使用旧的驱动,导致无法识别设备。Linux 不受此限制。 +- QQ 群文件中下载 RemoveGhostDev64.exe 可以自动删除所有 USB 注册的驱动信息,无需第一步 +- 禁止在中断中添加打印和耗时操作,否则会影响 USB 按照 interval 传输 \ No newline at end of file diff --git a/docs/zh/demo/usbd_audiov2.rst b/docs/zh/demo/usbd_audiov2.rst new file mode 100644 index 00000000..d329a29a --- /dev/null +++ b/docs/zh/demo/usbd_audiov2.rst @@ -0,0 +1,10 @@ +AudioV2 Device +================= + +在使用 UAC2.0 时,需要注意以下几点: + +- 在使用windows 时,当修改描述符任意参数时,必须同步修改字符串描述符,并且卸载驱动,否则windows会认为设备未更改,继续使用旧的驱动,导致无法识别设备。Linux 不受此限制。 +- QQ 群文件中下载 RemoveGhostDev64.exe 可以自动删除所有 USB 注册的驱动信息,无需第一步 +- windows 10 uac2.0 功能不完善,请使用 windows 11 测试uac2.0 功能。Linux 不受此限制 +- windows 中设置的采样率表范围在多通道时(通道数大于2)计算有误,比如设置 8K~96K,那么实际是大于等于8K 小于96K,而非小于等于96K。Linux 不受此限制 +- 禁止在中断中添加打印和耗时操作,否则会影响 USB 按照 interval 传输 \ No newline at end of file diff --git a/docs/zh/demo/usbd_cdc_acm.rst b/docs/zh/demo/usbd_cdc_acm.rst new file mode 100644 index 00000000..46bdc195 --- /dev/null +++ b/docs/zh/demo/usbd_cdc_acm.rst @@ -0,0 +1,104 @@ +CDC ACM Device +================= + +本 demo 主要用于演示 cdc acm 功能,参考 `demo/cdc_acm_template.c` 模板。包含收发测试,DTR 控制,ZLP 测试,性能测试。 + +- 开辟读写 buffer,用于收发数据,并且buffer需要用 nocache 修饰,这里我们读写都是用 2048字节,是为了后面的 ZLP 测试和性能测试使用。 + +.. code-block:: C + + USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t read_buffer[2048]; /* 2048 is only for test speed , please use CDC_MAX_MPS for common*/ + USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t write_buffer[2048]; + + +- 在协议栈事件回调中,我们需要在枚举完成后启动第一次传输,并清除相关 flag,可以在 reset 事件中清除,也可以在 configured 事件中清除。 + +.. code-block:: C + + static void usbd_event_handler(uint8_t busid, uint8_t event) + { + switch (event) { + case USBD_EVENT_RESET: + break; + case USBD_EVENT_CONNECTED: + break; + case USBD_EVENT_DISCONNECTED: + break; + case USBD_EVENT_RESUME: + break; + case USBD_EVENT_SUSPEND: + break; + case USBD_EVENT_CONFIGURED: + ep_tx_busy_flag = false; + /* setup first out ep read transfer */ + usbd_ep_start_read(busid, CDC_OUT_EP, read_buffer, 2048); + break; + case USBD_EVENT_SET_REMOTE_WAKEUP: + break; + case USBD_EVENT_CLR_REMOTE_WAKEUP: + break; + + default: + break; + } + } + +- 在接收完成中断中继续发起接收;在发送完成中断中判断是否需要发送 ZLP。 + +.. code-block:: C + + void usbd_cdc_acm_bulk_out(uint8_t busid, uint8_t ep, uint32_t nbytes) + { + USB_LOG_RAW("actual out len:%d\r\n", nbytes); + // for (int i = 0; i < 100; i++) { + // printf("%02x ", read_buffer[i]); + // } + // printf("\r\n"); + /* setup next out ep read transfer */ + usbd_ep_start_read(busid, CDC_OUT_EP, read_buffer, 2048); + } + + void usbd_cdc_acm_bulk_in(uint8_t busid, uint8_t ep, uint32_t nbytes) + { + USB_LOG_RAW("actual in len:%d\r\n", nbytes); + + if ((nbytes % usbd_get_ep_mps(busid, ep)) == 0 && nbytes) { + /* send zlp */ + usbd_ep_start_write(busid, CDC_IN_EP, NULL, 0); + } else { + ep_tx_busy_flag = false; + } + } + +- 以下是为了测试 DTR 功能并控制 USB 发送,DTR 和 RTS 只用于搭配 UART 使用,如果是纯 USB,没什么用,这里仅做测试。DTR 开关使用任意串口上位机并勾选 DTR。 + +.. code-block:: C + + void usbd_cdc_acm_set_dtr(uint8_t busid, uint8_t intf, bool dtr) + { + if (dtr) { + dtr_enable = 1; + } else { + dtr_enable = 0; + } + } + +- 在主函数中一直调用发送即可 + +.. code-block:: C + + void cdc_acm_data_send_with_dtr_test(uint8_t busid) + { + if (dtr_enable) { + ep_tx_busy_flag = true; + usbd_ep_start_write(busid, CDC_IN_EP, write_buffer, 2048); + while (ep_tx_busy_flag) { + } + } + } + +- 上述我们需要注意,长度设置为 2048 是为了测试 ZLP 功能,通常实际使用时,接收长度应该使用 CDC_MAX_MPS 。具体原因参考 :ref:`usb_ext` +- 如果需要做性能测试,使用 tools/test_srcipts/test_cdc_speed.py 进行测试,并在测试之前删除 `usbd_cdc_acm_bulk_out` 和 `usbd_cdc_acm_bulk_in` 中的打印,否则会影响测试结果。 + + +此外,对于 CDC ACM 搭配 OS 的情况,通常我们 read 使用异步并将数据存储到 ringbuffer 中,write 使用同步搭配 sem 使用。 \ No newline at end of file diff --git a/docs/zh/demo/usbd_ecm.rst b/docs/zh/demo/usbd_ecm.rst new file mode 100644 index 00000000..faf736f8 --- /dev/null +++ b/docs/zh/demo/usbd_ecm.rst @@ -0,0 +1,4 @@ +CDC ECM Device +================= + +ECM demo 参考 `demo/cdc_ecm*.c` 模板。 默认对接 lwip 协议栈,上层使用 lwip api 即可。 \ No newline at end of file diff --git a/docs/zh/demo/usbd_hid.rst b/docs/zh/demo/usbd_hid.rst new file mode 100644 index 00000000..acc1c5bb --- /dev/null +++ b/docs/zh/demo/usbd_hid.rst @@ -0,0 +1,4 @@ +HID Device +================= + +HID 功能比较简单,因此不作赘述,需要注意,使用 hid custom 例程时,需要搭配 `tools/test_srcipts/test_hid_inout.py` 使用(携带 report id功能)。 \ No newline at end of file diff --git a/docs/zh/demo/usbd_msc.rst b/docs/zh/demo/usbd_msc.rst new file mode 100644 index 00000000..1b09a7d2 --- /dev/null +++ b/docs/zh/demo/usbd_msc.rst @@ -0,0 +1,39 @@ +MSC Device +================= + +本节主要演示 USB 模拟 U 盘功能。默认使用RAM 作为存储介质模拟 U 盘。 + +- 实现 U 盘的读写和获取容量接口,注意,容量 block_num 为虚拟的,实际没有这么多 block,读写的数据超过 BLOCK_COUNT 会丢弃。 + +block_size 一般为 512/2048/4096。 + +.. code-block:: C + + void usbd_msc_get_cap(uint8_t busid, uint8_t lun, uint32_t *block_num, uint32_t *block_size) + { + *block_num = 1000; //Pretend having so many buffer,not has actually. + *block_size = BLOCK_SIZE; + } + int usbd_msc_sector_read(uint8_t busid, uint8_t lun, uint32_t sector, uint8_t *buffer, uint32_t length) + { + if (sector < BLOCK_COUNT) + memcpy(buffer, mass_block[sector].BlockSpace, length); + return 0; + } + + int usbd_msc_sector_write(uint8_t busid, uint8_t lun, uint32_t sector, uint8_t *buffer, uint32_t length) + { + if (sector < BLOCK_COUNT) + memcpy(mass_block[sector].BlockSpace, buffer, length); + return 0; + } + +- 默认上述 API 在中断中执行,如果需要在非中断中执行,可以选择如下: + +1,裸机下开启 `CONFIG_USBDEV_MSC_POLLING` 并在 while1 中调用 `usbd_msc_polling`,则读写函数在 while1 中执行。 + +2, OS 下开启 `CONFIG_USBDEV_MSC_THREAD`,则读写函数在线程中执行。 + +- 修改 `CONFIG_USBDEV_MSC_BUFSIZE` 会影响 U 盘的读写速度,必须是 block_size 的整数倍,当然,也会增加 RAM 的占用。 + +- 如果 RAM 例程可以用,但是介质更换成 SD 或者 FLASH 后不可用,则一定是介质驱动问题。 \ No newline at end of file diff --git a/docs/zh/demo/usbd_mtp.rst b/docs/zh/demo/usbd_mtp.rst new file mode 100644 index 00000000..13a5ceb8 --- /dev/null +++ b/docs/zh/demo/usbd_mtp.rst @@ -0,0 +1,6 @@ +MTP Device +================= + +MTP demo 参考 `demo/mtp_template.c` 模板。 默认适配 fatfs 文件系统(`platform/fatfs/usbd_fatfs_mtp.c`)。 + +.. note:: MTP 为商用收费,不开放 MTP 驱动源码,请联系官方购买授权。 \ No newline at end of file diff --git a/docs/zh/demo/usbd_rndis.rst b/docs/zh/demo/usbd_rndis.rst new file mode 100644 index 00000000..c90df8f8 --- /dev/null +++ b/docs/zh/demo/usbd_rndis.rst @@ -0,0 +1,4 @@ +CDC RNDIS Device +================= + +RNDIS demo 参考 `demo/cdc_rndis*.c` 模板。 默认对接 lwip 协议栈,上层使用 lwip api 即可。 \ No newline at end of file diff --git a/docs/zh/demo/usbd_vendor.rst b/docs/zh/demo/usbd_vendor.rst new file mode 100644 index 00000000..47c9ff41 --- /dev/null +++ b/docs/zh/demo/usbd_vendor.rst @@ -0,0 +1,44 @@ +Vendor Device 驱动编写 +=========================== + +本节主要介绍如何编写一个 vendor device 驱动。 + +- 首先复制一份 class/template/usbd_xxx.c 文件 +- 实现以下三个回调函数,通常来说,vendor 驱动只需要实现 vendor_handler + +.. code-block:: C + + intf->class_interface_handler = xxx_class_interface_request_handler; + intf->class_endpoint_handler = NULL; + intf->vendor_handler = NULL; + intf->notify_handler = xxx_notify_handler; + +- 举例如下 + +case1 演示对于主机 IN 数据的处理,将数据拷贝到 *data 中,并指定*len 的长度。协议栈会自动发送给主机,不需要用户手动调用发送 API。 + +case2 演示对于主机 OUT 数据的处理,当执行到此函数时,说明数据都已经接收完成,可以直接读取 *data 中的数据,长度为 *len。 + +.. code-block:: C + + static int xxx_vendor_request_handler(uint8_t busid, struct usb_setup_packet *setup, uint8_t **data, uint32_t *len) + { + USB_LOG_WRN("XXX Class request: " + "bRequest 0x%02x\r\n", + setup->bRequest); + + switch (setup->bRequest) { + case 1: + memcpy(*data, xxx, sizeof(xxx)); + *len = sizeof(xxx); + case 2: + hexdump(*data, *len); + default: + USB_LOG_WRN("Unhandled XXX Class bRequest 0x%02x\r\n", setup->bRequest); + return -1; + } + + return 0; + } + +- 最后使用形如 usbd_add_interface(busid, usbd_xxx_init_intf(&intf)) 注册接口 \ No newline at end of file diff --git a/docs/zh/demo/usbd_video.rst b/docs/zh/demo/usbd_video.rst new file mode 100644 index 00000000..2709c2e8 --- /dev/null +++ b/docs/zh/demo/usbd_video.rst @@ -0,0 +1,83 @@ +USB Video Device +================= + +本节主要演示 USB UAC 功能,支持 YUYV, MJPEG, H264 格式。为了方便演示,都采用的静态图。 + +demo 包含 **video_static_yuyv_template**, **video_static_mjpeg_template**, **video_static_h264_template**, 仅描述符和图片数据不同。 + +- 在高速模式下,默认最大是1024字节,但是如果芯片支持 additional transcations,可以配置为最高 2048字节或者3072字节,这样可以提高传输效率。 + +.. code-block:: C + + #ifdef CONFIG_USB_HS + #define MAX_PAYLOAD_SIZE 1024 // for high speed with one transcations every one micro frame + #define VIDEO_PACKET_SIZE (unsigned int)(((MAX_PAYLOAD_SIZE / 1)) | (0x00 << 11)) + + // #define MAX_PAYLOAD_SIZE 2048 // for high speed with two transcations every one micro frame + // #define VIDEO_PACKET_SIZE (unsigned int)(((MAX_PAYLOAD_SIZE / 2)) | (0x01 << 11)) + + // #define MAX_PAYLOAD_SIZE 3072 // for high speed with three transcations every one micro frame + // #define VIDEO_PACKET_SIZE (unsigned int)(((MAX_PAYLOAD_SIZE / 3)) | (0x02 << 11)) + + #else + #define MAX_PAYLOAD_SIZE 1020 + #define VIDEO_PACKET_SIZE (unsigned int)(((MAX_PAYLOAD_SIZE / 1)) | (0x00 << 11)) + #endif + +- 通常只需要修改 WIDTH 和 HEIGHT + +.. code-block:: C + + #define WIDTH (unsigned int)(640) + #define HEIGHT (unsigned int)(480) + + #define CAM_FPS (30) + #define INTERVAL (unsigned long)(10000000 / CAM_FPS) + #define MIN_BIT_RATE (unsigned long)(WIDTH * HEIGHT * 16 * CAM_FPS) //16 bit + #define MAX_BIT_RATE (unsigned long)(WIDTH * HEIGHT * 16 * CAM_FPS) + #define MAX_FRAME_SIZE (unsigned long)(WIDTH * HEIGHT * 2) + +- USB 端点配置,默认 interval 为 1,也就是全速模式下 1ms,高速模式下 125us。同步类型使用异步模式。 + +.. code-block:: C + + /* 1.2.2.2 Standard VideoStream Isochronous Video Data Endpoint Descriptor */ + USB_ENDPOINT_DESCRIPTOR_INIT(VIDEO_IN_EP, 0x05, VIDEO_PACKET_SIZE, 0x01), + + +- 使用 `usbd_video_stream_start_write` 传输数据, 最后 **do_copy** 选项表示是否将数据 copy 到 packet_buffer, +如果不选择 copy, 则会直接在原图像数据中填充头部信息,并直接发送,达到 zero copy 功能。 + +- 因为提供的是静态数据,不能被修改,因此需要重新给一个 frame_buffer 用于图像传输,在实际对接 camera 场景中是动态数据,直接使用 camera 的数据缓冲区即可。 + + +.. code-block:: C + + void usbd_video_iso_callback(uint8_t busid, uint8_t ep, uint32_t nbytes) + { + if (usbd_video_stream_split_transfer(busid, ep)) { + /* one frame has done */ + iso_tx_busy = false; + } + } + + USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t packet_buffer[MAX_PAYLOAD_SIZE]; + USB_NOCACHE_RAM_SECTION USB_MEM_ALIGNX uint8_t frame_buffer[32 * 1024]; + + void video_test(uint8_t busid) + { + memset(packet_buffer, 0, sizeof(packet_buffer)); + + while (1) { + if (tx_flag) { + iso_tx_busy = true; + memcpy(frame_buffer, cherryusb_mjpeg, sizeof(cherryusb_mjpeg)); // cherryusb_mjpeg is a static MJPEG frame buffer, so we need copy it to frame_buffer + usbd_video_stream_start_write(busid, VIDEO_IN_EP, packet_buffer, (uint8_t *)frame_buffer, sizeof(cherryusb_mjpeg), false); + while (iso_tx_busy) { + if (tx_flag == 0) { + break; + } + } + } + } + } \ No newline at end of file diff --git a/docs/zh/demo/usbd_webusb.rst b/docs/zh/demo/usbd_webusb.rst new file mode 100644 index 00000000..fab7850b --- /dev/null +++ b/docs/zh/demo/usbd_webusb.rst @@ -0,0 +1,21 @@ +WebUSB Device +================= + +本 demo 主要演示 webusb 功能,webusb 主要用于弹出网页并对 USB 设备进行访问。示例使用 webusb_hid_template.c。 + +- 在注册描述符时注册 BOS, MSOSV2, WEBUSB 描述符即可。 + +.. code-block:: C + + usbd_bos_desc_register(busid, &bos_desc); + usbd_msosv2_desc_register(busid, &msosv2_desc); + usbd_webusb_desc_register(busid, &webusb_url_desc); + +- 增加一个接口描述符用于 webusb + +.. code-block:: C + + USB_INTERFACE_DESCRIPTOR_INIT(USBD_WEBUSB_INTF_NUM, 0x00, 0x00, 0xff, 0x00, 0x00, 0x00) + +- 其余使用 hid 描述符,不再赘述 +- 枚举完成后,电脑右下角会弹出网页信息,点击即可打开网页 \ No newline at end of file diff --git a/docs/zh/demo/usbd_winusb.rst b/docs/zh/demo/usbd_winusb.rst new file mode 100644 index 00000000..aab0ad17 --- /dev/null +++ b/docs/zh/demo/usbd_winusb.rst @@ -0,0 +1,55 @@ +WinUSB Device +================= + +本节主要介绍 winusb 驱动。winusb 是 windows 为了让用户友好的访问 USB 自定义类设备提供的一套通用驱动,其实本质就是 CDC ACM,只不过没有设置波特率的命令。 +WINUSB 版本根据 USB 版本分为 V1/V2 版本,V2 版本需要包含 BOS 描述符,V1 版本不需要。 **V2 版本需要在设备描述符中设置为 USB2.1 的版本号**。 + +.. note:: 更换 winusb 描述符任意配置可能会枚举成功但是无法识别设备,需要删除 计算机\HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\usbflags 下所有注册表项,重新插拔设备后生效。 + +- V1 版本注册描述符 + +.. code-block:: C + + const struct usb_descriptor winusbv1_descriptor = { + .device_descriptor_callback = device_descriptor_callback, + .config_descriptor_callback = config_descriptor_callback, + .device_quality_descriptor_callback = device_quality_descriptor_callback, + .string_descriptor_callback = string_descriptor_callback, + .msosv1_descriptor = &msosv1_desc + }; + + OR + + usbd_msosv1_desc_register(busid, &msosv1_desc); + +- V2 版本注册描述符 + +.. code-block:: C + + const struct usb_descriptor winusbv2_descriptor = { + .device_descriptor_callback = device_descriptor_callback, + .config_descriptor_callback = config_descriptor_callback, + .device_quality_descriptor_callback = device_quality_descriptor_callback, + .string_descriptor_callback = string_descriptor_callback, + .msosv2_descriptor = &msosv2_desc, + .bos_descriptor = &bos_desc, + }; + + OR + + usbd_bos_desc_register(busid, &bos_desc); + usbd_msosv2_desc_register(busid, &msosv2_desc); + + +- 接口描述符注册 + +.. code-block:: C + + /* Interface 0 */ + USB_INTERFACE_DESCRIPTOR_INIT(0x00, 0x00, 0x02, 0xFF, 0x00, 0x00, 0x02), + /* Endpoint OUT 2 */ + USB_ENDPOINT_DESCRIPTOR_INIT(WINUSB_OUT_EP, USB_ENDPOINT_TYPE_BULK, WINUSB_EP_MPS, 0x00), + /* Endpoint IN 1 */ + USB_ENDPOINT_DESCRIPTOR_INIT(WINUSB_IN_EP, USB_ENDPOINT_TYPE_BULK, WINUSB_EP_MPS, 0x00), + +- 读写操作与 CDC ACM 相同,不再赘述 \ No newline at end of file diff --git a/docs/zh/demo/usbh_audio.rst b/docs/zh/demo/usbh_audio.rst new file mode 100644 index 00000000..18933801 --- /dev/null +++ b/docs/zh/demo/usbh_audio.rst @@ -0,0 +1,4 @@ +Audio Host +================= + +.. note:: Host UAC 为商用收费,请联系官方购买授权。 \ No newline at end of file diff --git a/docs/zh/demo/usbh_bluetooth.rst b/docs/zh/demo/usbh_bluetooth.rst new file mode 100644 index 00000000..5b06f502 --- /dev/null +++ b/docs/zh/demo/usbh_bluetooth.rst @@ -0,0 +1,2 @@ +BTBLE Host +================= diff --git a/docs/zh/demo/usbh_hid.rst b/docs/zh/demo/usbh_hid.rst new file mode 100644 index 00000000..2719bf70 --- /dev/null +++ b/docs/zh/demo/usbh_hid.rst @@ -0,0 +1,55 @@ +HID Host +================= + +本节主要介绍 Host HID 类的使用。 + +- HID 枚举完成回调中创建一次性线程 + +.. code-block:: C + + + void usbh_hid_run(struct usbh_hid *hid_class) + { + usb_osal_thread_create("usbh_hid", 2048, CONFIG_USBHOST_PSC_PRIO + 1, usbh_hid_thread, hid_class); + } + + void usbh_hid_stop(struct usbh_hid *hid_class) + { + } + + +- 这里我们使用 usbh_submit_urb 的异步操作,在中断中处理数据并继续接收下一次数据。 + +.. code-block:: C + + static void usbh_hid_thread(void *argument) + { + int ret; + struct usbh_hid *hid_class = (struct usbh_hid *)argument; + ; + + /* test with only one buffer, if you have more hid class, modify by yourself */ + + /* Suggest you to use timer for int transfer and use ep interval */ + usbh_int_urb_fill(&hid_class->intin_urb, hid_class->hport, hid_class->intin, hid_buffer, hid_class->intin->wMaxPacketSize, 0, usbh_hid_callback, hid_class); + ret = usbh_submit_urb(&hid_class->intin_urb); + if (ret < 0) { + goto delete; + } + // clang-format off + delete: + usb_osal_thread_delete(NULL); + // clang-format on + } + +- 当然,也可以不使用异步操作,而是使用 timeout 的同步操作。 +- HID 使用的是中断传输,因此正常来说,我们需要根据 **bInterval** 来设置定时器,定时触发中断传输,demo 这里没有使用,如果对时间有精确要求,可以选择使用定时器来触发异步发送。 +- 以 hub 通信为例,采用的是一次性定时器,也可以使用周期性定时器。 + +.. code-block:: C + + hub->int_timer = usb_osal_timer_create("hubint_tim", USBH_GET_URB_INTERVAL(hub->intin->bInterval, hport->speed) / 1000, hub_int_timeout, hub, 0); + +.. note:: + + 这里的 `USBH_GET_URB_INTERVAL` 是一个宏定义,用于根据 binterval 计算 URB 的传输间隔时间, 单位是 us,而定时器最低是 ms ,因此需要除以 1000。对于小于等于 1ms 的不需要使用定时器。 \ No newline at end of file diff --git a/docs/zh/demo/usbh_msc.rst b/docs/zh/demo/usbh_msc.rst new file mode 100644 index 00000000..524dc5c1 --- /dev/null +++ b/docs/zh/demo/usbh_msc.rst @@ -0,0 +1,56 @@ +MSC Host +================= + +本节主要介绍 Host MSC 的使用。借助 FATFS 实现读写功能。 + +- 在 msc 枚举完成的回调中注册一个线程,用于读写操作。 + +.. code-block:: C + + void usbh_msc_run(struct usbh_msc *msc_class) + { + usb_osal_thread_create("usbh_msc", 2048, CONFIG_USBHOST_PSC_PRIO + 1, usbh_msc_thread, msc_class); + } + + void usbh_msc_stop(struct usbh_msc *msc_class) + { + } + + +- 不使用 fatfs,则直接使用 usbh_msc_scsi_read10 或者 usbh_msc_scsi_write10 函数进行读写操作。 +- 如果使用 fatfs,则需要在 usbh_msc_thread 中调用 fatfs 的接口进行读写操作。msc读写适配fatfs 参考 `platform/fatfs/usbh_fatfs.c` + +.. code-block:: C + + static void usbh_msc_thread(void *argument) + { + int ret; + struct usbh_msc *msc_class = (struct usbh_msc *)argument; + + /* test with only one buffer, if you have more msc class, modify by yourself */ + #if 1 + /* get the partition table */ + ret = usbh_msc_scsi_read10(msc_class, 0, partition_table, 1); + if (ret < 0) { + USB_LOG_RAW("scsi_read10 error,ret:%d\r\n", ret); + goto delete; + } + for (uint32_t i = 0; i < 512; i++) { + if (i % 16 == 0) { + USB_LOG_RAW("\r\n"); + } + USB_LOG_RAW("%02x ", partition_table[i]); + } + USB_LOG_RAW("\r\n"); + #endif + + #if TEST_USBH_MSC_FATFS + usb_msc_fatfs_test(); + #endif + // clang-format off + delete: + usb_osal_thread_delete(NULL); + // clang-format on + } + +- 最后处理完成或者失败后,删除线程。 \ No newline at end of file diff --git a/docs/zh/demo/usbh_net.rst b/docs/zh/demo/usbh_net.rst new file mode 100644 index 00000000..1516f397 --- /dev/null +++ b/docs/zh/demo/usbh_net.rst @@ -0,0 +1,156 @@ +Network Host +================= + +本节主要介绍 Host USB 网卡的使用,当前已经支持和测试以下 USB 网卡: + +- 4G 网卡:EC20(ECM/RNDIS)、手机(RNDIS)、SIMCOM7600(RNDIS)、ML307R(RNDIS)、AIR780(RNDIS) + +.. caution:: 请注意,部分 4G 网卡默认不带自动拨号功能,请更换固件或者使用 AT 配置成自动拨号,否则无法获取 IP。 + +- USB 以太网卡:ASIX AX88772,REALTEK RTL8152 +- USB WIFI 网卡: 博流 BL616(RNDIS/ECM) + +USB 网卡相关的宏和文件 +------------------------ + +网卡相关的宏如下,主要用于根据不同的网络组件注册网卡驱动: + +.. code-block:: C + + // #define CONFIG_USBHOST_PLATFORM_CDC_ECM + // #define CONFIG_USBHOST_PLATFORM_CDC_RNDIS + // #define CONFIG_USBHOST_PLATFORM_CDC_NCM + // #define CONFIG_USBHOST_PLATFORM_ASIX + // #define CONFIG_USBHOST_PLATFORM_RTL8152 + +.. note:: 如果使用了 Kconfig 系统,上述宏自定生成,其他平台请手动定义。 + +USB 网卡传输层面已经对接好了相关网络组件,列举如下: + +- 自定义 OS + LWIP 请使用 **platform/lwip/usbh_lwip.c**,需要自行包含该文件,并使能上述相关的宏。并在初始化 USB 之前调用 `tcpip_init(NULL, NULL)` +- RT-THREAD + LWIP 请使用 **platform/rtthread/usbh_lwip.c**,在 Kconfig 中使能对应的网卡驱动后自动勾选该文件,勾选 rt-thread lwip以后自动调用 `tcpip_init(NULL, NULL)` +- ESP-IDF + LWIP 请使用 **platform/freertos/usbh_net.c**,在 Kconfig 中使能对应的网卡驱动后自动勾选该文件,并且在初始化 USB 之前调用 `esp_netif_init()` + `esp_event_loop_create_default()` +- NUTTX + NUTTX 网络组件 请使用 **platform/nuttx/usbh_net.c**,在 Kconfig 中使能对应的网卡驱动后自动勾选该文件,勾选网络组件以后自动调用 + +.. note:: 如果是自行添加代码,别忘了添加 USB 网卡驱动相关的源文件,例如 **class/usbh_cdc_ecm.c**。所以我们推荐搭配对应平台使用哦,省去自己添加文件的麻烦 + +USB 网卡对接过程 +------------------- + +下面举例对接 LWIP 的对接过程。 + +- 在 USB 网卡枚举完成以后,会 **自动** 调用 `usbh_xxx_run` 函数,此时注册 netif 驱动,并且开启 DHCP 客户端和获取 IP 的定时器。 + +.. code-block:: C + + void usbh_cdc_ecm_run(struct usbh_cdc_ecm *cdc_ecm_class) + { + struct netif *netif = &g_cdc_ecm_netif; + + netif->hwaddr_len = 6; + memcpy(netif->hwaddr, cdc_ecm_class->mac, 6); + + IP4_ADDR(&g_ipaddr, 0, 0, 0, 0); + IP4_ADDR(&g_netmask, 0, 0, 0, 0); + IP4_ADDR(&g_gateway, 0, 0, 0, 0); + + netif = netif_add(netif, &g_ipaddr, &g_netmask, &g_gateway, NULL, usbh_cdc_ecm_if_init, tcpip_input); + netif_set_default(netif); + while (!netif_is_up(netif)) { + } + + dhcp_handle = usb_osal_timer_create("dhcp", 200, dhcp_timeout, netif, true); + if (dhcp_handle == NULL) { + USB_LOG_ERR("timer creation failed! \r\n"); + while (1) { + } + } + + usb_osal_thread_create("usbh_cdc_ecm_rx", 2048, CONFIG_USBHOST_PSC_PRIO + 1, usbh_cdc_ecm_rx_thread, NULL); + #if LWIP_DHCP + dhcp_start(netif); + usb_osal_timer_start(dhcp_handle); + #endif + } + +- `usbh_lwip_eth_output_common` 用于将发送 pbuf 组装成 USB 网卡数据包 +- `usbh_lwip_eth_input_common` 用于将 USB 网卡数据组装成 pbuf +- 实际网卡发送和接收处理 + +.. code-block:: C + + static err_t usbh_cdc_ecm_linkoutput(struct netif *netif, struct pbuf *p) + { + int ret; + (void)netif; + + usbh_lwip_eth_output_common(p, usbh_cdc_ecm_get_eth_txbuf()); + ret = usbh_cdc_ecm_eth_output(p->tot_len); + if (ret < 0) { + return ERR_BUF; + } else { + return ERR_OK; + } + } + + void usbh_cdc_ecm_eth_input(uint8_t *buf, uint32_t buflen) + { + usbh_lwip_eth_input_common(&g_cdc_ecm_netif, buf, buflen); + } + +- USB 网卡 拔出以后会 **自动** 调用 `usbh_xxx_stop` 函数,此时需要停止 DHCP 客户端,删除定时器,并且移除 netif。 + +.. code-block:: C + + void usbh_cdc_ecm_stop(struct usbh_cdc_ecm *cdc_ecm_class) + { + struct netif *netif = &g_cdc_ecm_netif; + (void)cdc_ecm_class; + + #if LWIP_DHCP + dhcp_stop(netif); + dhcp_cleanup(netif); + usb_osal_timer_delete(dhcp_handle); + #endif + netif_set_down(netif); + netif_remove(netif); + } + +- 因为 USB 网卡内部已经对接了LWIP,因此用户可以直接使用 LWIP 的 API,无需关心 USB 的实现。 + +USB 网卡 LWIP 配置宏相关注意事项 +------------------------------------ + +**LWIP_TCPIP_CORE_LOCKING_INPUT** 用于不使用 lwip 内置的 tcpip 线程,而使用 USB 自己的接收处理线程。 + +**LWIP_TCPIP_CORE_LOCKING** 在现在 lwip 版本中默认是打开的,也推荐必须打开。 + +**PBUF_POOL_BUFSIZE** 推荐大于1600,搭配 LWIP_TCPIP_CORE_LOCKING_INPUT 使用,因为我们提供了使用 zero mempy 的方式,使用静态 pbuf,而不是把数据 copy 到 pbuf 中。 + +**TCPIP_THREAD_STACKSIZE** 推荐大于 1K,防止栈溢出。 + +.. code-block:: C + + #if LWIP_TCPIP_CORE_LOCKING_INPUT != 1 + #warning suggest you to set LWIP_TCPIP_CORE_LOCKING_INPUT to 1, usb handles eth input with own thread + #endif + + #if LWIP_TCPIP_CORE_LOCKING != 1 + #error must set LWIP_TCPIP_CORE_LOCKING to 1 + #endif + + #if PBUF_POOL_BUFSIZE < 1600 + #error PBUF_POOL_BUFSIZE must be larger than 1600 + #endif + + #if TCPIP_THREAD_STACKSIZE < 1024 + #error TCPIP_THREAD_STACKSIZE must be >= 1024 + #endif + + +总结 +-------------- + +.. note:: 通过以上内容,我们可以看到 CherryUSB 对 USB 网卡的支持是非常完善的,用户只需要使能对应的宏或者勾选,就可以实现 USB 网卡的自动识别和驱动注册,无需手动初始化网卡相关配置,用户只需关注应用层,极大地方便了用户的使用。 + +具体移植文章可以参考开发者的一些笔记 https://club.rt-thread.org/ask/article/5cf3e9e0b2d95800.html \ No newline at end of file diff --git a/docs/zh/demo/usbh_serial.rst b/docs/zh/demo/usbh_serial.rst new file mode 100644 index 00000000..e37a6959 --- /dev/null +++ b/docs/zh/demo/usbh_serial.rst @@ -0,0 +1,196 @@ +Serial Host +================= + +本节主要介绍 Host serial 框架的使用。Serial 框架当前支持 cdc acm, ftdi, cp210x, ch34x, pl2303,gsm 驱动。 + +.. figure:: img/usbh_serial.png + +当前支持两种使用方式,一种是使用源生 CherryUSB usbhost serial API 进行操作,另一种是基于平台封装的 API 操作,比如 rt-thread device API,nuttx posix API。 + +下面演示的是使用 CherryUSB usbhost serial API 进行串口回环测试,并且使用阻塞发送,异步读取的方式: + +.. code-block:: C + + struct usbh_serial *serial; + + serial = usbh_serial_open("/dev/ttyACM0", USBH_SERIAL_O_RDWR | USBH_SERIAL_O_NONBLOCK); + if (serial == NULL) { + serial = usbh_serial_open("/dev/ttyUSB0", USBH_SERIAL_O_RDWR | USBH_SERIAL_O_NONBLOCK); + if (serial == NULL) { + USB_LOG_RAW("no serial device found\r\n"); + goto delete; + } + } + + struct usbh_serial_termios termios; + + memset(&termios, 0, sizeof(termios)); + termios.baudrate = 115200; + termios.stopbits = 0; + termios.parity = 0; + termios.databits = 8; + termios.rtscts = false; + termios.rx_timeout = 0; + ret = usbh_serial_control(serial, USBH_SERIAL_CMD_SET_ATTR, &termios); + if (ret < 0) { + USB_LOG_RAW("set serial attr error, ret:%d\r\n", ret); + goto delete_with_close; + } + + serial_tx_bytes = 0; + while (1) { + ret = usbh_serial_write(serial, serial_tx_buffer, sizeof(serial_tx_buffer)); + if (ret < 0) { + USB_LOG_RAW("serial write error, ret:%d\r\n", ret); + goto delete_with_close; + } else { + serial_tx_bytes += ret; + + if (serial_tx_bytes == SERIAL_TEST_LEN) { + USB_LOG_RAW("send over\r\n"); + break; + } + } + } + + volatile uint32_t wait_timeout = 0; + serial_rx_bytes = 0; + while (1) { + ret = usbh_serial_read(serial, &serial_rx_data[serial_rx_bytes], SERIAL_TEST_LEN - serial_rx_bytes); + if (ret < 0) { + USB_LOG_RAW("serial read error, ret:%d\r\n", ret); + goto delete_with_close; + } else { + serial_rx_bytes += ret; + + if (serial_rx_bytes == SERIAL_TEST_LEN) { + USB_LOG_RAW("receive over\r\n"); + for (uint32_t i = 0; i < SERIAL_TEST_LEN; i++) { + if (serial_rx_data[i] != 0xa5) { + USB_LOG_RAW("serial loopback data error at index %d, data: 0x%02x\r\n", (unsigned int)i, serial_rx_data[i]); + goto delete_with_close; + } + } + serial_test_success = true; + break; + } + } + wait_timeout++; + + if (wait_timeout > 500) { // 5s + USB_LOG_RAW("serial read timeout\r\n"); + goto delete_with_close; + } + + usb_osal_msleep(10); + } + + usbh_serial_close(serial); + +.. caution:: 需要注意,例程中使用的是比较简单的先发送后读取的方式,因此发送的总长度不可以超过 CONFIG_USBHOST_SERIAL_RX_SIZE,正常使用 TX/RX 请分开进行。 + +用户需要考虑以下三种场景: + +- USB2TTL 设备 + 启用了波特率(USB2TTL设备必须启用波特率),这种情况下需要使用 `usbh_serial_write` 和 `usbh_serial_read` 进行收发数据, **并且 read 操作需要及时,防止 ringbuf 数据溢出而丢包**。不可以使用 `usbh_serial_cdc_write_async` 和 `usbh_serial_cdc_read_async` + +- 纯 USB 设备 + 未启动波特率,这种情况下可以使用 `usbh_serial_cdc_write_async` 和 `usbh_serial_cdc_read_async` 进行异步收发数据。阻塞则可以用 `usbh_serial_write` ,不可以使用 `usbh_serial_read`。 + +- 纯 USB 设备 + 启动波特率,同 1,但是接收速率会打折扣(因为多了一层 ringbuf)。此时也不可以使用 `usbh_serial_cdc_write_async` 和 `usbh_serial_cdc_read_async`。 **如果是 GSM 设备请使用第一种场景**。 + +.. note:: 简单来说就是,如果接收数据需要用到ringbuf转一层的,请使用第一种场景。 + +.. code-block:: C + + [I/usbh_hub] New full-speed device on Bus 0, Hub 1, Port 1 connected + [I/usbh_core] New device found,idVendor:10c4,idProduct:ea60,bcdDevice:0100 + [I/usbh_core] The device has 1 bNumConfigurations + [I/usbh_core] The device has 1 interfaces + [I/usbh_core] Enumeration success, start loading class driver + [I/usbh_core] Loading cp210x class driver on interface 0 + [I/usbh_cp210x] chip partnum: 0x02 + [I/usbh_cp210x] ulAmountInInQueue: 0, ulAmountInOutQueue: 0 + [I/usbh_serial] Ep=81 Attr=02 Mps=64 Interval=00 Mult=00 + [I/usbh_serial] Ep=01 Attr=02 Mps=64 Interval=00 Mult=00 + [I/usbh_serial] Register Serial Class: /dev/ttyUSB0 (cp210x) + start serial loopback test, len: 1024 + send over + receive over + serial loopback test success + [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB0 (cp210x) + [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected + [I/usbh_hub] New high-speed device on Bus 0, Hub 1, Port 1 connected + [I/usbh_core] New device found,idVendor:0403,idProduct:6010,bcdDevice:0700 + [I/usbh_core] The device has 1 bNumConfigurations + [I/usbh_core] The device has 2 interfaces + [I/usbh_core] Enumeration success, start loading class driver + [I/usbh_core] Loading ftdi class driver on interface 0 + [I/usbh_ftdi] chip name: FT2232H + [I/usbh_serial] Ep=81 Attr=02 Mps=512 Interval=00 Mult=00 + [I/usbh_serial] Ep=02 Attr=02 Mps=512 Interval=00 Mult=00 + [I/usbh_serial] Register Serial Class: /dev/ttyUSB0 (ftdi) + [I/usbh_core] Loading ftdi class driver on interface 1 + [I/usbh_ftdi] chip name: FT2232H + [I/usbh_serial] Ep=83 Attr=02 Mps=512 Interval=00 Mult=00 + [I/usbh_serial] Ep=04 Attr=02 Mps=512 Interval=00 Mult=00 + [I/usbh_serial] Register Serial Class: /dev/ttyUSB1 (ftdi) + start serial loopback test, len: 1024 + send over + receive over + serial loopback test success + [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB0 (ftdi) + [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB1 (ftdi) + [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected + [I/usbh_hub] New full-speed device on Bus 0, Hub 1, Port 1 connected + [I/usbh_core] New device found,idVendor:067b,idProduct:2303,bcdDevice:0300 + [I/usbh_core] The device has 1 bNumConfigurations + [I/usbh_core] The device has 1 interfaces + [I/usbh_core] Enumeration success, start loading class driver + [I/usbh_core] Loading pl2303 class driver on interface 0 + [I/usbh_pl2303] Ep=81 Attr=03 Mps=10 Interval=01 Mult=00 + [I/usbh_pl2303] chip type: PL2303HX + [I/usbh_serial] Ep=02 Attr=02 Mps=64 Interval=00 Mult=00 + [I/usbh_serial] Ep=83 Attr=02 Mps=64 Interval=00 Mult=00 + [I/usbh_serial] Register Serial Class: /dev/ttyUSB0 (pl2303) + start serial loopback test, len: 1024 + send over + receive over + serial loopback test success + [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB0 (pl2303) + [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected + [W/usbh_hub] Failed to enable port 1 + [I/usbh_hub] New full-speed device on Bus 0, Hub 1, Port 1 connected + [I/usbh_core] New device found,idVendor:1a86,idProduct:7523,bcdDevice:0264 + [I/usbh_core] The device has 1 bNumConfigurations + [I/usbh_core] The device has 1 interfaces + [I/usbh_core] Enumeration success, start loading class driver + [I/usbh_core] Loading ch34x class driver on interface 0 + [I/usbh_ch43x] Ep=81 Attr=03 Mps=8 Interval=01 Mult=00 + [I/usbh_ch43x] chip version: 0x31 + [I/usbh_serial] Ep=82 Attr=02 Mps=32 Interval=00 Mult=00 + [I/usbh_serial] Ep=02 Attr=02 Mps=32 Interval=00 Mult=00 + [I/usbh_serial] Register Serial Class: /dev/ttyUSB0 (ch34x) + start serial loopback test, len: 1024 + send over + receive over + serial loopback test success + [I/usbh_serial] Unregister Serial Class: /dev/ttyUSB0 (ch34x) + [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected + [I/usbh_hub] New full-speed device on Bus 0, Hub 1, Port 1 connected + [I/usbh_core] New device found,idVendor:42bf,idProduct:b210,bcdDevice:0217 + [I/usbh_core] The device has 1 bNumConfigurations + [I/usbh_core] The device has 3 interfaces + [I/usbh_core] Enumeration success, start loading class driver + [E/usbh_core] Do not support Class:0xff, Subclass:0x01, Protocl:0x00 on interface 0 + [I/usbh_core] Loading cdc_acm class driver on interface 1 + [I/usbh_cdc_acm] Ep=85 Attr=03 Mps=64 Interval=00 Mult=00 + [I/usbh_serial] Ep=04 Attr=02 Mps=64 Interval=00 Mult=00 + [I/usbh_serial] Ep=83 Attr=02 Mps=64 Interval=00 Mult=00 + [I/usbh_serial] Register Serial Class: /dev/ttyACM0 (cdc_acm) + [I/usbh_core] Loading cdc_data class driver on interface 2 + start serial loopback test, len: 1024 + send over + receive over + serial loopback test success + [I/usbh_serial] Unregister Serial Class: /dev/ttyACM0 (cdc_acm) + [I/usbh_core] Device on Bus 0, Hub 1, Port 1 disconnected + diff --git a/docs/zh/demo/usbh_vendor.rst b/docs/zh/demo/usbh_vendor.rst new file mode 100644 index 00000000..a0b0bb7b --- /dev/null +++ b/docs/zh/demo/usbh_vendor.rst @@ -0,0 +1,127 @@ +Vendor Host 驱动编写 +=========================== + +本节主要介绍如何编写一个 vendor host 驱动。 + +- 首先复制一份 class/template/usbh_xxx.c 文件 + +- 定义 class 驱动并使用 CLASS_INFO_DEFINE 前缀,这样,枚举完成后,协议栈自动通过 usbd_class_find_driver 来查找对应的驱动。 + +.. code-block:: C + + static const struct usbh_class_driver xxx_class_driver = { + .driver_name = "xxx", + .connect = usbh_xxx_connect, + .disconnect = usbh_xxx_disconnect + }; + + CLASS_INFO_DEFINE const struct usbh_class_info xxx_class_info = { + .match_flags = USB_CLASS_MATCH_INTF_CLASS | USB_CLASS_MATCH_INTF_SUBCLASS | USB_CLASS_MATCH_INTF_PROTOCOL, + .bInterfaceClass = 0, + .bInterfaceSubClass = 0, + .bInterfaceProtocol = 0, + .id_table = NULL, + .class_driver = &xxx_class_driver + }; + + +- 实现 connect 和 disconnect 函数, 在 connect 函数中,需要分配一个 xxx_class 结构体,在 disconnect 函数中释放 urb 和 xxx_class。 + +.. code-block:: C + + struct usbh_xxx { + struct usbh_hubport *hport; + struct usb_endpoint_descriptor *xxxin; + struct usb_endpoint_descriptor *xxxout; + struct usbh_urb xxxin_urb; + struct usbh_urb xxxout_urb; + + uint8_t intf; /* interface number */ + uint8_t minor; + + void *user_data; + }; + + static int usbh_xxx_connect(struct usbh_hubport *hport, uint8_t intf) + { + struct usb_endpoint_descriptor *ep_desc; + int ret; + + struct usbh_xxx *xxx_class = usbh_xxx_class_alloc(); + if (xxx_class == NULL) { + USB_LOG_ERR("Fail to alloc xxx_class\r\n"); + return -USB_ERR_NOMEM; + } + + return ret; + } + + + static int usbh_xxx_disconnect(struct usbh_hubport *hport, uint8_t intf) + { + int ret = 0; + + struct usbh_xxx *xxx_class = (struct usbh_xxx *)hport->config.intf[intf].priv; + + if (xxx_class) { + if (xxx_class->xxxin) { + usbh_kill_urb(&xxx_class->xxxin_urb); + } + + if (xxx_class->xxxout) { + usbh_kill_urb(&xxx_class->xxxout_urb); + } + + if (hport->config.intf[intf].devname[0] != '\0') { + USB_LOG_INFO("Unregister xxx Class:%s\r\n", hport->config.intf[intf].devname); + usbh_xxx_stop(xxx_class); + } + + usbh_xxx_class_free(xxx_class); + } + + return ret; + } + +- 初始化端点 + +.. code-block:: C + + for (uint8_t i = 0; i < hport->config.intf[intf].altsetting[0].intf_desc.bNumEndpoints; i++) { + ep_desc = &hport->config.intf[intf].altsetting[0].ep[i].ep_desc; + if (ep_desc->bEndpointAddress & 0x80) { + USBH_EP_INIT(xxx_class->intin, ep_desc); + } else { + USBH_EP_INIT(xxx_class->intout, ep_desc); + } + } + +- 最后设计收发 API,根据实际情况设计成同步 or 异步。 + +.. code-block:: C + + int usbh_xxx_in_transfer(struct usbh_xxx *xxx_class, uint8_t *buffer, uint32_t buflen, uint32_t timeout) + { + int ret; + struct usbh_urb *urb = &xxx_class->xxxin_urb; + + usbh_xxx_urb_fill(urb, xxx_class->hport, xxx_class->xxxin, buffer, buflen, timeout, NULL, NULL); + ret = usbh_submit_urb(urb); + if (ret == 0) { + ret = urb->actual_length; + } + return ret; + } + + int usbh_xxx_out_transfer(struct usbh_xxx *xxx_class, uint8_t *buffer, uint32_t buflen, uint32_t timeout) + { + int ret; + struct usbh_urb *urb = &xxx_class->xxxout_urb; + + usbh_xxx_urb_fill(urb, xxx_class->hport, xxx_class->xxxout, buffer, buflen, timeout, NULL, NULL); + ret = usbh_submit_urb(urb); + if (ret == 0) { + ret = urb->actual_length; + } + return ret; + } \ No newline at end of file diff --git a/docs/zh/demo/usbh_video.rst b/docs/zh/demo/usbh_video.rst new file mode 100644 index 00000000..7de4b457 --- /dev/null +++ b/docs/zh/demo/usbh_video.rst @@ -0,0 +1,4 @@ +Video Host +================= + +.. note:: Host UVC 为商用收费,请联系官方购买授权。 \ No newline at end of file diff --git a/docs/zh/demo/usbh_wifi.rst b/docs/zh/demo/usbh_wifi.rst new file mode 100644 index 00000000..588e8131 --- /dev/null +++ b/docs/zh/demo/usbh_wifi.rst @@ -0,0 +1,2 @@ +WIFI Host +================= diff --git a/docs/zh/index.rst b/docs/zh/index.rst new file mode 100644 index 00000000..343fe322 --- /dev/null +++ b/docs/zh/index.rst @@ -0,0 +1,160 @@ +.. CherryUSB 使用指南 documentation master file, created by + sphinx-quickstart on Thu Nov 21 10:50:33 2019. + You can adapt this file completely to your liking, but it should at least + contain the root `toctree` directive. + +CherryUSB 使用指南 +====================================================== + +CherryUSB 是一个小而美的、可移植性高的、用于嵌入式系统的 USB 主从协议栈。同时 CherryUSB 具有以下优点: + +**易于学习 USB** + +为了方便用户学习 USB 基本知识、枚举、驱动加载、IP 驱动,因此,编写的代码具备以下优点: + +- 代码精简,逻辑简单,无复杂 C 语言语法 +- 树状化编程,代码层层递进 +- Class 驱动和 porting 驱动模板化、精简化 +- API 分类清晰(从机:初始化、注册类、命令回调类、数据收发类;主机:初始化、查找类、数据收发类) + +**易于使用 USB** + +为了方便用户使用 USB 接口,考虑到用户学习过 uart 和 dma,因此,设计的数据收发类接口具备以下优点: + +- 等价于使用 uart tx dma/uart rx dma +- 收发长度没有限制,用户不需要关心 USB 分包过程(porting 驱动做分包过程) + +**易于发挥 USB 性能** + +考虑到 USB 性能问题,尽量达到 USB 硬件理论带宽,因此,设计的数据收发类接口具备以下优点: + +- Porting 驱动直接对接寄存器,无抽象层封装 +- Memory zero copy +- IP 如果带 DMA 则使用 DMA 模式(DMA 带硬件分包功能) +- 长度无限制,方便对接硬件 DMA 并且发挥 DMA 的优势 +- 分包功能在中断中处理 + +**从机协议栈整体执行流程** + +.. figure:: usbdev.svg + +**主机协议栈整体执行流程** + +.. figure:: usbhost.svg + +**其他相关链接** + +- **视频教程**: https://www.bilibili.com/cheese/play/ss707687201 +- **github** : https://github.com/sakumisu/CherryUSB +- **CherryUSB原理性分析和应用实践-汉斯期刊**: https://www.hanspub.org/journal/paperinformation?paperid=126903 + +.. toctree:: + :maxdepth: 1 + :caption: 快速上手 + + quick_start/start + quick_start/demo + quick_start/transplant + quick_start/rtthread + quick_start/q&a + quick_start/migration + quick_start/share + quick_start/opensource + +.. toctree:: + :maxdepth: 1 + :caption: USB 基本知识点 + + usb/usb2.0_basic + usb/usb3.0_basic + usb/usb_desc + usb/usb_request + usb/usb_enum + usb/usb_ext + +.. toctree:: + :maxdepth: 1 + :caption: API 手册 + + api/api_device + api/api_host + api/api_port + api/api_config + +.. toctree:: + :maxdepth: 1 + :caption: Class 指南 + + class/class_cdc + class/class_hid + class/class_msc + class/class_audio + class/class_video + class/winusb + +.. toctree:: + :maxdepth: 1 + :caption: 例程 + + demo/usbd_cdc_acm + demo/usbd_hid + demo/usbd_msc + demo/usbd_audiov1 + demo/usbd_audiov2 + demo/usbd_video + demo/usbd_winusb + demo/usbd_webusb + demo/usbd_rndis + demo/usbd_ecm + demo/usbd_adb + demo/usbd_mtp + demo/usbh_serial + demo/usbh_hid + demo/usbh_msc + demo/usbh_net + demo/usbh_bluetooth + demo/usbh_wifi + demo/usbh_audio + demo/usbh_video + demo/usb_otg + demo/usbd_vendor + demo/usbh_vendor + +.. toctree:: + :maxdepth: 1 + :caption: USBIP 介绍 + + usbip/ohci + usbip/ehci + usbip/xhci + usbip/chipidea + usbip/dwc2 + usbip/musb + usbip/fotg210 + usbip/cdns2 + usbip/cdns3 + usbip/dwc3 + +.. toctree:: + :maxdepth: 1 + :caption: 工具使用 + + tools/index + +.. toctree:: + :maxdepth: 1 + :caption: 版本说明 + + version + +.. toctree:: + :maxdepth: 1 + :caption: 性能展示 + + show/index + +.. toctree:: + :maxdepth: 1 + :caption: 商业支持 + + support/index diff --git a/docs/zh/quick_start/demo.rst b/docs/zh/quick_start/demo.rst new file mode 100644 index 00000000..2cadfb13 --- /dev/null +++ b/docs/zh/quick_start/demo.rst @@ -0,0 +1,314 @@ +基于现有 demo 快速验证 +========================= + +在学习 USB 或者是学习 CherryUSB 代码之前,我们需要先基于现有的 demo 进行快速验证,为什么?是为了提升对 USB 的兴趣,能有信心进行下一步的动作,如果 demo 都跑不起来,或者自己摸索写代码,或者先看 USB 基本概念,结果看到最后, +发现一点都看不懂,概念好多,根本记不住,从而丧失对 USB 的兴趣。因此,先跑 demo 非常重要。下面我将给大家罗列目前支持的 demo 仓库。 + +基于 bouffalolab 系列芯片(官方 SDK 支持) +------------------------------------------ + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/cherryusb_bouffalolab + - FOTG210 + - less than latest + +基于 HPMicro 系列芯片(官方 SDK 支持) +----------------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/cherryusb_hpmicro + - CHIPIDEA + - less than latest + +基于 esp32s2/s3/p4 系列芯片(官方 SDK 支持) +------------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/cherryusb_esp32 + - DWC2 + - less than latest + +默认 demo 采用组件库安装的形式,在 https://components.espressif.com/ 中搜索 cherryusb 即可。也可使用官方 idf 仓库下的 cherryusb demo。 + +ESP-Registry 可以参考官方文档,推荐使用 vscode + esp-idf 的开发环境。 + +- ctrl + shift + p 选择 ESP-IDF 欢迎界面,然后选择 Component mananger + +.. figure:: img/esp1.png + +- 找到 cherryusb 并安装 + +.. figure:: img/esp2.png + +- 打开 menuconfig,并打开 cherryusb 的配置,根据实际情况选择主机或者从机模式 + +.. figure:: img/esp3.png +.. figure:: img/esp4.png + +基于 Phytium 系列芯片(官方 SDK 支持) +--------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://gitee.com/phytium_embedded/phytium-free-rtos-sdk + - PUSB2/XHCI + - equal to v1.4.0 + +基于 Essemi 系列芯片(官方 SDK 支持) +----------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/cherryusb_es32 + - MUSB + - less than latest + +基于 Artinchip 系列芯片(官方 SDK 支持) +----------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://gitee.com/artinchip/luban-lite + - AIC/EHCI/OHCI + - less than latest + +基于 Kendryte canmv-k230 系列(官方 SDK 支持) +----------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/k230_sdk + - DWC2 + - less than latest + +基于 NXP MCX 系列芯片 +--------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/cherryusb_mcx https://github.com/RT-Thread/rt-thread/tree/master/bsp/nxp/mcx + - CHIPIDEA/kinetis + - less than latest + +基于 SiFli SF32 系列芯片(官方 SDK 支持) +-------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/OpenSiFli/SiFli-SDK + - MUSB + - less than latest + +基于 RP2040/RP2035 芯片(官方 SDK 即将支持) +-------------------------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/pico-examples https://github.com/CherryUSB/pico-sdk + - RP2040 + - less than latest + +基于 Actionstech 系列芯片(官方 SDK 支持) +------------------------------------------------------ + +Not opensource, 请联系 Actionstech 官方 + +基于 ST 系列芯片 +--------------------------- + +.. list-table:: + :widths: 10 10 10 + :header-rows: 1 + + * - Repo url + - USB IP + - Version + * - https://github.com/CherryUSB/cherryusb_stm32 + - DWC2/FSDEV + - less than latest + +默认提供以下 demo 工程: + +- F103 使用 fsdev ip +- F429 主从使用 USB1, 引脚 pb14/pb15, 默认从机没有开启 DMA 模式 +- H7 设备使用 USB0, 引脚 pa11/pa12,没有开 DMA 模式。主机使用 USB1 ,引脚 pb14/pb15,并且需要做 nocache 处理 + +demo 底下提供了 **stm32xxx.ioc** 文件,双击打开,点击 **Generate Code** 即可。 + +.. caution:: 生成完以后,请使用 git reset 功能将被覆盖的 `main.c` 和 `stm32xxx_it.c` 文件撤回,禁止被 cubemx 覆盖。 + +涵盖 F1/F4/H7,其余芯片基本类似,不再赘述,具体区别有: + +- usb ip 区别:F1使用 fsdev,F4/H7使用 dwc2 +- dwc2 ip 区别: USB0 (引脚是 PA11/PA12) 和 USB1 (引脚是 PB14/PB15), 其中 USB1 默认全速,可以接外部PHY 形成高速主机,并且带 dma 功能 +- F4 无 cache,H7 有 cache + +如果是 STM32F7/STM32H7 这种带 cache 功能,需要将 usb 使用到的 ram 定位到 no cache ram 区域。举例如下 + +.. code-block:: C + + cpu_mpu_config(0, MPU_Normal_NonCache, 0x24070000, MPU_REGION_SIZE_64KB); + +对应 keil 中的 sct 脚本修改: + +.. code-block:: C + + LR_IROM1 0x08000000 0x00200000 { ; load region size_region + ER_IROM1 0x08000000 0x00200000 { ; load address = execution address + *.o (RESET, +First) + *(InRoot$$Sections) + .ANY (+RO) + .ANY (+XO) + } + RW_IRAM2 0x24000000 0x00070000 { ; RW data + .ANY (+RW +ZI) + } + USB_NOCACHERAM 0x24070000 0x00010000 { ; RW data + *(.noncacheable) + } + } + +USB Device 移植要点 +^^^^^^^^^^^^^^^^^^^^^^ + +- 使用 **stm32cubemx** 创建工程,配置基本的 RCC、UART (作为log使用) + +.. figure:: img/stm32_1.png +.. figure:: img/stm32_2.png + +- 如果使用 fsdev ip,勾选 **USB** 。如果使用 dwc2 ip,勾选 **USB_OTG_FS** 或者勾选 **USB_OTG_HS**。开启 USB 中断,其他配置对我们没用,代码中不会使用任何 st 的 usb 库。 + +.. figure:: img/stm32_3_1.png +.. figure:: img/stm32_3_2.png + +- 配置 usb clock 为 48M + +.. figure:: img/stm32_4_1.png +.. figure:: img/stm32_4_2.png + +- 选择好工程,这里我们选择 keil,设置好 stack 和 heap,如果使用 msc 可以推荐设置大点,然后点击 **Generate Code**。 + +.. figure:: img/stm32_5.png + +- 添加 CherryUSB 必须要的源码( **usbd_core.c** 、 **dwc2/usb_dc_dwc2.c** 或者是 **fsdev/usb_dc_fsdev.c** ),以及想要使用的 class 驱动,可以将对应的 class template 添加方便测试。 + +.. figure:: img/stm32_6.png + +- 头文件该加的加 + +.. figure:: img/stm32_7.png + +- 复制一份 **cherryusb_config_template.h**,放到 `Core/Inc` 目录下,并命名为 `usb_config.h` + +.. figure:: img/stm32_8.png + +- 如果使用 fsdev ip,(V1.5.0 开始需要增加 **fsdev/usb_glue_st.c**) 在 `usb_config.h` 中实现以下宏,具体数值不同芯片不一样: + +.. code-block:: C + + #define CONFIG_USBDEV_FSDEV_PMA_ACCESS 2 + +- 编译器推荐使用 **AC6**。勾选 **Microlib**,并实现 **printf** ,方便后续查看 log。 + +.. figure:: img/stm32_10.png +.. figure:: img/stm32_11.png + +.. note :: 以下两个步骤从 V1.5.0 开始不再需要,**fsdev/usb_glue_st.c**, **dwc2/usb_glue_st.c** 文件中已经实现 + +- 拷贝 **xxx_msp.c** 中的 **HAL_PCD_MspInit** 函数中的内容到 **usb_dc_low_level_init** 函数中,屏蔽 st 生成的 usb 初始化 + +.. figure:: img/stm32_12.png +.. figure:: img/stm32_14.png + +- 在中断函数中调用 `USBD_IRQHandler`,并传入 `busid` + +.. figure:: img/stm32_13.png + +- 如果芯片带 cache,cache 修改参考 :ref:`usb_cache` 章节 + +- 调用 template 的内容初始化,并填入 `busid` 和 USB IP 的 `reg base`, `busid` 从 0 开始,不能超过 `CONFIG_USBDEV_MAX_BUS` + +.. figure:: img/stm32_15.png + +USB Host 移植要点 +^^^^^^^^^^^^^^^^^^^^^^ + +前面 6 步与 Device 一样。需要注意,host 驱动只支持带 dma 的 hs port (引脚是 PB14/PB15),所以 fs port (引脚是 PA11/PA12)不做支持(没有 dma 你玩什么主机)。 + +- 添加 CherryUSB 必须要的源码( **usbh_core.c** 、 **usbh_hub.c** 、 **usb_hc_dwc2.c** 、 **usb_glue_st.c** 以及 **osal** 目录下的适配层文件),以及想要使用的 class 驱动,并且可以将对应的 **usb host.c** 添加方便测试。 + +.. figure:: img/stm32_16.png + +- 编译器推荐使用 **AC6**。勾选 **Microlib**,并实现 **printf** ,方便后续查看 log。 + +.. figure:: img/stm32_10.png +.. figure:: img/stm32_11.png + +- 复制一份 **cherryusb_config_template.h**,放到 `Core/Inc` 目录下,并命名为 `usb_config.h` + +.. note :: 以下两个步骤从 V1.5.0 开始不再需要,**fsdev/usb_glue_st.c**, **dwc2/usb_glue_st.c** 文件中已经实现 + +- 拷贝 **xxx_msp.c** 中的 `HAL_HCD_MspInit` 函数中的内容到 `usb_hc_low_level_init` 函数中,屏蔽 st 生成的 usb 初始化 +- 在中断函数中调用 `USBH_IRQHandler`,并传入 `busid` + +.. figure:: img/stm32_19.png + +- 链接脚本修改参考 :ref:`usbh_link_script` 章节 +- 如果芯片带 cache,cache 修改参考 :ref:`usb_cache` 章节 +- 调用 `usbh_initialize` 并填入 `busid` 和 USB IP 的 `reg base` 还有 `event_handler` 可缺省为NULL, `busid` 从 0 开始,不能超过 `CONFIG_USBHOST_MAX_BUS` +- 启动线程 + +.. figure:: img/stm32_18.png diff --git a/docs/zh/quick_start/img/env0.png b/docs/zh/quick_start/img/env0.png new file mode 100644 index 00000000..c0a8b03f Binary files /dev/null and b/docs/zh/quick_start/img/env0.png differ diff --git a/docs/zh/quick_start/img/env1.png b/docs/zh/quick_start/img/env1.png new file mode 100644 index 00000000..2a68e052 Binary files /dev/null and b/docs/zh/quick_start/img/env1.png differ diff --git a/docs/zh/quick_start/img/env2.png b/docs/zh/quick_start/img/env2.png new file mode 100644 index 00000000..ee37101a Binary files /dev/null and b/docs/zh/quick_start/img/env2.png differ diff --git a/docs/zh/quick_start/img/esp1.png b/docs/zh/quick_start/img/esp1.png new file mode 100644 index 00000000..1f059e71 Binary files /dev/null and b/docs/zh/quick_start/img/esp1.png differ diff --git a/docs/zh/quick_start/img/esp2.png b/docs/zh/quick_start/img/esp2.png new file mode 100644 index 00000000..fd20e9ce Binary files /dev/null and b/docs/zh/quick_start/img/esp2.png differ diff --git a/docs/zh/quick_start/img/esp3.png b/docs/zh/quick_start/img/esp3.png new file mode 100644 index 00000000..82a7162f Binary files /dev/null and b/docs/zh/quick_start/img/esp3.png differ diff --git a/docs/zh/quick_start/img/esp4.png b/docs/zh/quick_start/img/esp4.png new file mode 100644 index 00000000..ffb2882a Binary files /dev/null and b/docs/zh/quick_start/img/esp4.png differ diff --git a/docs/zh/quick_start/img/question1.png b/docs/zh/quick_start/img/question1.png new file mode 100644 index 00000000..a852e6aa Binary files /dev/null and b/docs/zh/quick_start/img/question1.png differ diff --git a/docs/zh/quick_start/img/question2.png b/docs/zh/quick_start/img/question2.png new file mode 100644 index 00000000..e00b3bfa Binary files /dev/null and b/docs/zh/quick_start/img/question2.png differ diff --git a/docs/zh/quick_start/img/stm32_1.png b/docs/zh/quick_start/img/stm32_1.png new file mode 100644 index 00000000..b91044a5 Binary files /dev/null and b/docs/zh/quick_start/img/stm32_1.png differ diff --git a/docs/zh/quick_start/img/stm32_10.png b/docs/zh/quick_start/img/stm32_10.png new file mode 100644 index 00000000..d55b38e7 Binary files /dev/null and b/docs/zh/quick_start/img/stm32_10.png differ diff --git a/docs/zh/quick_start/img/stm32_11.png b/docs/zh/quick_start/img/stm32_11.png new file mode 100644 index 00000000..3ad5b074 Binary files /dev/null and b/docs/zh/quick_start/img/stm32_11.png differ diff --git a/docs/zh/quick_start/img/stm32_12.png b/docs/zh/quick_start/img/stm32_12.png new file mode 100644 index 00000000..84aaffe8 Binary files /dev/null and b/docs/zh/quick_start/img/stm32_12.png differ diff --git a/docs/zh/quick_start/img/stm32_13.png b/docs/zh/quick_start/img/stm32_13.png new file mode 100644 index 00000000..f12fad75 Binary files /dev/null and b/docs/zh/quick_start/img/stm32_13.png differ diff --git a/docs/zh/quick_start/img/stm32_14.png b/docs/zh/quick_start/img/stm32_14.png new file mode 100644 index 00000000..e5aa5b19 Binary files /dev/null and b/docs/zh/quick_start/img/stm32_14.png differ diff --git a/docs/zh/quick_start/img/stm32_15.png b/docs/zh/quick_start/img/stm32_15.png new file mode 100644 index 00000000..7c293287 Binary files /dev/null and b/docs/zh/quick_start/img/stm32_15.png differ diff --git a/docs/zh/quick_start/img/stm32_16.png b/docs/zh/quick_start/img/stm32_16.png new file mode 100644 index 00000000..70f2e63c Binary files /dev/null and b/docs/zh/quick_start/img/stm32_16.png differ diff --git a/docs/zh/quick_start/img/stm32_18.png b/docs/zh/quick_start/img/stm32_18.png new file mode 100644 index 00000000..456df189 Binary files /dev/null and b/docs/zh/quick_start/img/stm32_18.png differ diff --git a/docs/zh/quick_start/img/stm32_19.png b/docs/zh/quick_start/img/stm32_19.png new file mode 100644 index 00000000..a796dc75 Binary files /dev/null and b/docs/zh/quick_start/img/stm32_19.png differ diff --git a/docs/zh/quick_start/img/stm32_2.png b/docs/zh/quick_start/img/stm32_2.png new file mode 100644 index 00000000..671b1b82 Binary files /dev/null and b/docs/zh/quick_start/img/stm32_2.png differ diff --git a/docs/zh/quick_start/img/stm32_3_1.png b/docs/zh/quick_start/img/stm32_3_1.png new file mode 100644 index 00000000..9e42196d Binary files /dev/null and b/docs/zh/quick_start/img/stm32_3_1.png differ diff --git a/docs/zh/quick_start/img/stm32_3_2.png b/docs/zh/quick_start/img/stm32_3_2.png new file mode 100644 index 00000000..492d6739 Binary files /dev/null and b/docs/zh/quick_start/img/stm32_3_2.png differ diff --git a/docs/zh/quick_start/img/stm32_4_1.png b/docs/zh/quick_start/img/stm32_4_1.png new file mode 100644 index 00000000..e81437bc Binary files /dev/null and b/docs/zh/quick_start/img/stm32_4_1.png differ diff --git a/docs/zh/quick_start/img/stm32_4_2.png b/docs/zh/quick_start/img/stm32_4_2.png new file mode 100644 index 00000000..dd90f5b8 Binary files /dev/null and b/docs/zh/quick_start/img/stm32_4_2.png differ diff --git a/docs/zh/quick_start/img/stm32_5.png b/docs/zh/quick_start/img/stm32_5.png new file mode 100644 index 00000000..5bec9878 Binary files /dev/null and b/docs/zh/quick_start/img/stm32_5.png differ diff --git a/docs/zh/quick_start/img/stm32_6.png b/docs/zh/quick_start/img/stm32_6.png new file mode 100644 index 00000000..f0ad9a0b Binary files /dev/null and b/docs/zh/quick_start/img/stm32_6.png differ diff --git a/docs/zh/quick_start/img/stm32_7.png b/docs/zh/quick_start/img/stm32_7.png new file mode 100644 index 00000000..8aef0bfa Binary files /dev/null and b/docs/zh/quick_start/img/stm32_7.png differ diff --git a/docs/zh/quick_start/img/stm32_8.png b/docs/zh/quick_start/img/stm32_8.png new file mode 100644 index 00000000..08d2e724 Binary files /dev/null and b/docs/zh/quick_start/img/stm32_8.png differ diff --git a/docs/zh/quick_start/migration.rst b/docs/zh/quick_start/migration.rst new file mode 100644 index 00000000..10f2ef7e --- /dev/null +++ b/docs/zh/quick_start/migration.rst @@ -0,0 +1,63 @@ +部分改动迁移指南 +======================== + + +usbh_initialize +------------------ + +usbh_initialize 从 v1.6.0 开始新增 event_handler 参数,通常不需要使用,可以传入 NULL。 + +dwc2 glue st +---------------- + +dwc2 从 v1.5.0 开始 glue 文件内置底层初始化,比如 `usb_dc_low_level_init`,底层依赖 `HAL_PCD_MspInit` 和 `HAL_HCD_MspInit`,必须使用 stm32cubemx 生成。第三方平台不保证有这些函数实现,自行检查。 + + +dwc2 glue +---------------- + +dwc2 从 v1.5.1 开始新增 `struct dwc2_user_params`,用于实现多 dwc2 port 不同配置。并替代 `usbd_get_dwc2_gccfg_conf` 和 `usbh_get_dwc2_hccfg_conf` 函数, +并增加 `dwc2_get_user_params` 函数实现,举例如下: + +.. code-block:: C + + #ifndef CONFIG_USB_DWC2_CUSTOM_PARAM + void dwc2_get_user_params(uint32_t reg_base, struct dwc2_user_params *params) + { + memcpy(params, ¶m_common, sizeof(struct dwc2_user_params)); + #ifdef CONFIG_USB_DWC2_CUSTOM_FIFO + struct usb_dwc2_user_fifo_config s_dwc2_fifo_config; + + dwc2_get_user_fifo_config(reg_base, &s_dwc2_fifo_config); + + params->device_rx_fifo_size = s_dwc2_fifo_config.device_rx_fifo_size; + for (uint8_t i = 0; i < MAX_EPS_CHANNELS; i++) { + params->device_tx_fifo_size[i] = s_dwc2_fifo_config.device_tx_fifo_size[i]; + } + #endif + } + #endif + +host serial +---------------- + +从 v1.6.0 开始,主机增加 host serial 框架,用于统一所有类串口设备。以下 API 需要使用新 serial API 替换: + +.. code-block:: C + + int usbh_xxx_set_line_coding(struct usbh_xxx *xxx_class, struct cdc_line_coding *line_coding); + int usbh_xxx_get_line_coding(struct usbh_xxx *xxx_class, struct cdc_line_coding *line_coding); + int usbh_xxx_set_line_state(struct usbh_xxx *xxx_class, bool dtr, bool rts); + + int usbh_xxx_bulk_in_transfer(struct usbh_xxx *xxx_class, uint8_t *buffer, uint32_t buflen, uint32_t timeout); + int usbh_xxx_bulk_out_transfer(struct usbh_xxx *xxx_class, uint8_t *buffer, uint32_t buflen, uint32_t timeout); + +替换为: + +.. code-block:: C + + struct usbh_serial *usbh_serial_open(const char *devname, uint32_t open_flags); + int usbh_serial_close(struct usbh_serial *serial); + int usbh_serial_control(struct usbh_serial *serial, int cmd, void *arg); + int usbh_serial_write(struct usbh_serial *serial, const void *buffer, uint32_t buflen); + int usbh_serial_read(struct usbh_serial *serial, void *buffer, uint32_t buflen); diff --git a/docs/zh/quick_start/opensource.rst b/docs/zh/quick_start/opensource.rst new file mode 100644 index 00000000..7990538e --- /dev/null +++ b/docs/zh/quick_start/opensource.rst @@ -0,0 +1,62 @@ +官方开源项目分享 +==================== + +除了基本的厂家 SDK 支持以外,我们还对一些火热的开源项目进行了支持,以便于开发者更好的使用这些项目。下面列举适配的 demo 工程链接,具体适配层参考 https://github.com/cherry-embedded/CherryUSB/tree/master/platform 。 + +DAPLINK +-------------- + +适配链接:https://github.com/cherry-embedded/CherryDAP + +Blackmagic +-------------- + +适配链接:https://github.com/zhangjiance/bmp-hpm-port + +RT-Thread +-------------- + +适配链接:https://github.com/RT-Thread/rt-thread + +NUTTX/VELA +-------------- + +适配链接:https://github.com/CherryUSB/cherryusb_nuttx + +Zephyr +-------------- + +适配链接:https://github.com/hpmicro/zephyr_sdk_glue + +Cangaroo +-------------- + +Cangaroo is an open source can bus analyzer software. We provide four-channel CANFD analyzer based on hpmicro hpm5361 + +适配上位机链接:https://github.com/RCSN/cangaroo_hpmicro_canfd_analyzer +适配下位机链接:https://github.com/RCSN/hpm_sdk_extra/tree/main/demos/cangaroo_hpmicro + +LVGL +-------------- + +适配链接:https://github.com/cherry-embedded/CherryUSB/tree/master/platform/lvgl + +QMK +-------------- + +QMK is an open-source keyboard firmware for Atmel AVR and Arm USB families. + +适配链接:待开放 + +Klipper +-------------- + +Klipper is a 3d-printer firmware. + +适配链接:待开放 + + +MAKCU/KMBOX +-------------- + +懂的都懂,不开放 \ No newline at end of file diff --git a/docs/zh/quick_start/q&a.rst b/docs/zh/quick_start/q&a.rst new file mode 100644 index 00000000..391b7037 --- /dev/null +++ b/docs/zh/quick_start/q&a.rst @@ -0,0 +1,137 @@ +Q & A +============================== + +移植提问模板 +---------------- + +请在下列途径提交问题: +- RT-Thread 官方论坛: https://club.rt-thread.org/ask/tag/5f5f851966917b14.html +- Github issue: https://github.com/cherry-embedded/CherryUSB/issues/new/choose + +提问中请包含以下信息: + +- 使用的版本 +- 使用的板子,引脚,USB IP +- 是否配置 USB 中断,USB 时钟,USB 引脚,USB phy 配置,以及 USB 寄存器地址是否正确,截图 +- 是否能进 USB 中断 +- 芯片是否带有 cache功能,是否做了 no cache 处理,截图 +- USB 电路是否画正确,是否使用杜邦线连接,是否直连,如果正常,请说明正常原因 +- 如果能进中断,配置 **#define CONFIG_USB_DBG_LEVEL USB_DBG_LOG** 并提供 log,仅限商业 IP, 其余 IP 禁止开启 log,否则无法枚举 +- 是否流片并销售 + +其余问题提问模板 +------------------ + +具体说明现象,复现方式,使用我提供的 demo 再测试,以及提供完整 log + +CherryUSB 性能能到多少 +---------------------------------------------------------------- + +参考 :ref:`performace_show` + +ST IP 命名问题 +------------------ + +ST 命名为 USB_OTG_FS, USB_OTG_HS,并不是说明本身是高速或者全速,只是代表可以支持到高速,但是本身都是全速,需要外挂高速phy。因此,提问禁止说这两个词,请使用 USB0(PA11/PA12),USB1(PB14/PB15) 代替。其余国产厂家同理。 + +GD IP 问题 +------------------ + +GD IP 采用 DWC2,但是读取的硬件参数都是 0(我也不懂为什么不给人知道),因此需要用户自行知道硬件信息,从 1.5.0 开始由于需要读取硬件信息,因此无法直接使用。 + +其次 GD 复位以后无法使用 EPDIS 功能关闭端点,需要用户删除 reset 中断中的以下代码: + +.. code-block:: C + + USB_OTG_INEP(i)->DIEPCTL = (USB_OTG_DIEPCTL_EPDIS | USB_OTG_DIEPCTL_SNAK); + USB_OTG_OUTEP(i)->DOEPCTL = (USB_OTG_DOEPCTL_EPDIS | USB_OTG_DOEPCTL_SNAK); + +除此之外可能存在其他未知 BUG,请自行测试。 + +开启 USB_LOG_DBG 后无法枚举 +---------------------------------------------------------------- + +有且仅有商业性 IP 开启后可以枚举,其余 IP 禁止开启,否则无法枚举。懂得都懂。 + +USB3 CV测试用哪个版本 +------------------------------ + +1.4.3 版本及以上 + +Ep addr XXX fifo overflow +------------------------------ + +.. figure:: img/question1.png + +该错误表示该端点默认设置的 fifo 空间不够用,需要增大 fifo 空间,通常见于 DWC2/MUSB IP。FIFO 设置参考相关的 glue 文件。 + +Ep addr XXX overflow +------------------------------ + +.. figure:: img/question2.png + +该错误表示该 IP 硬件上没有这么多端点, 请更换 IP or 减少端点使用。 +当然也可以修改为双向端点,考虑到不是所有的 IP 都支持双向端点,因此默认 demo 不做双向功能,举例默认是 81 02 这样的而不是 81 01,如果支持,自行修改。某些 IP 双向端点可能会占用相同的硬件信息,不一定能同时使用,自行检查。 + +This dwc2 version does not support dma mode, so stop working +---------------------------------------------------------------- + +该 DWC2 版本不支持 dma 模式,禁止使用。不使用 DMA 模式会频繁触发 NAK 中断(大概几十us一次),CPU 占用率过高。 + +OTG 有哪些芯片支持 +------------------------------ + +当前主线仅 HPM 芯片支持 OTG 功能,通过 ID 引脚自动切换主从模式,其他芯片请使用手动切换模式 OR 自行实现添加 ID 识别的驱动。 + +PC 识别的 COM 口如何更改名称 +---------------------------------------------------------------- + +这是微软对 CDC ACM 的驱动问题,无法修改,如需修改,请联系微软并缴纳费用+编写驱动后即可更改。 + +connect 和 disconnect event 不触发 +---------------------------------------------------------------- + +当前仅 hpm 芯片支持 connect 和 disconnect 事件,其他芯片请使用 USB 检测 vbus 电路。DWC2 IP 支持,但是由于需要占用引脚,并且大多是log 口,然后不同使能的配置也不一样,因此不做支持。 + +__has_include 报错 +------------------------------------------------------------------ +如果报错,需要编译器支持 c99 语法,如果是 keil,请用 ac6 编译器 + +CONFIG_USB_HS 何时使用 +---------------------------------------------------------------- + +当你的芯片硬件支持高速,并想初始化成高速模式时开启,相关 IP 会根据该宏配置内部或者外部 高速 PHY。 + +Failed to enable port +---------------------------------------------------------------- + +供电不足或者硬件 USB 电路问题 + +移植 usb host 出现 urb 返回 -12/-14 +---------------------------------------------------------------- + +检查 phy 配置,cache 配置(如果有),电源供电(建议自供电) + +USB_ERR_NAK 说明 +---------------------------------------------------------------- + +USB_ERR_NAK 只存在于 DWC2 buffer dma/slave 模式(我们不使用 slave 模式),DWC2 在 buffer dma模式下对于中断传输不支持硬件处理 NAK 中断,因此需要软件处理,导致 NAK 中断非常多,建议搭配定时器使用。 +DWC2 scatter/gather dma 模式下全部由硬件处理,但是不支持 split 传输。总结, **食之无味,弃之可惜**。 + +USB host 连接 USB 网卡问题 +---------------------------------------------------------------- + +表现为能识别网卡并且分配到 IP 地址,但是无法 ping 通,这是因为网卡自身需要开启自动拨号,通常需要使用 AT 口设置。具体为 EC20/ML307 等模块。 + + +什么时候需要开启 CONFIG_USB_DCACHE_ENABLE +------------------------------------------------- + +当芯片带有 cache 功能,并且没有使用 no cache ram 时需要开启此宏以保证数据一致性。 **使用 EHCI 时,内部依旧需要使用 nocache ram**。通常,对于第三方平台或者组件,没有使用 no cache ram 宏修饰,都是使用全局变量或者 malloc 等 +操作,这部分 RAM 通常是走 cache 的,因此需要开启此宏。建议第三方平台使用时,必须开启。 + +哪些 IP 对数据有对齐要求 +------------------------------------------------- + +- 在未开启 CONFIG_USB_DCACHE_ENABLE 时,仅 DWC2/WCH/AIC IP 需要 4字节对齐,其余 1字节对齐即可。 +- 在开启 CONFIG_USB_DCACHE_ENABLE 时,所有 IP 都需要对齐到 CONFIG_USB_ALIGN_SIZE 字节 \ No newline at end of file diff --git a/docs/zh/quick_start/rtthread.rst b/docs/zh/quick_start/rtthread.rst new file mode 100644 index 00000000..132015d9 --- /dev/null +++ b/docs/zh/quick_start/rtthread.rst @@ -0,0 +1,62 @@ +基于 RT-Thread 软件包开发指南 +=============================== + +.. note:: CherryUSB 已经加入 RT-Thread 主线,可以选择使用主线版本,配置方式相同。 + +本节主要介绍使用 RT-Thread 提供的软件包管理器来配置工程,以 env 作为演示。本节操作不同芯片都一样,后续不再重复讲解。打开 env 以后使用 menuconfig 进入包管理器,并在如图所示路径中选择 CherryUSB。 + +.. figure:: img/env0.png + +从机配置 +-------------------------- + +* 选择 Enable usb device mode 并敲回车进入。 +* 首先第一个配置是配置 USB 的速度,分为 **FS、HS**,表示使用全速还是高速功能。高速功能要求内置高速 PHY 或者外接 PHY +* 其次第二个配置则是选择 USB device ip,不清楚自己芯片是哪个 ip 的可以参考 **port** 目录下对应的 readme。 +* 选择你想使用的 class +* 选择是否使用 demo 模板 + +.. figure:: img/env1.png + +* 最后退出保存即可。 +* 拷贝 `cherryusb_config_template.h` 文件到自己工程目录下,命名为 `usb_config.h`,并添加相应的目录头文件路径,并修改以下内容: + +.. code-block:: C + + #include "rtthread.h" + + #define CONFIG_USB_PRINTF(...) rt_kprintf(__VA_ARGS__) + +* USB IP 相关的 config 需要用户自己根据芯片实际情况修改 +* 在代码中实现 `usb_dc_low_level_init` 函数 +* 在 USB 中断函数中调用 `USBD_IRQHandler`,并传入 `busid` +* 调用 `usbd_initialize` 并填入 `busid` 和 USB IP 的 `reg base`, `busid` 从 0 开始,不能超过 `CONFIG_USBDEV_MAX_BUS` +* 使用 `scons --target=mdk5` 或者 `scons` 进行编译,如果是mdk,需要使用 AC6 编译器 +* 如果芯片带 cache,cache 修改参考 :ref:`usb_cache` 章节 + +主机配置 +-------------------------- + +* 选择 Enable usb host mode 并敲回车进入 +* 选择 USB host ip,不清楚自己芯片是哪个 ip 的可以参考 **port** 目录下对应的 readme +* 根据需要勾选 class 驱动 +* 选择是否开启模板 demo,推荐不用 + +.. figure:: img/env2.png + +* 最后退出保存即可。 +* 拷贝 `cherryusb_config_template.h` 文件到自己工程目录下,命名为 `usb_config.h`,并添加相应的目录头文件路径,并实现以下内容: + +.. code-block:: C + + #include "rtthread.h" + + #define CONFIG_USB_PRINTF(...) rt_kprintf(__VA_ARGS__) + +* USB IP 相关的 config 需要用户自己根据芯片实际情况修改 +* 在代码中实现 `usb_hc_low_level_init` 函数 +* 在 USB 中断函数中调用 `USBH_IRQHandler`,并传入 `busid` +* 调用 `usbh_initialize` 并填入 `busid` 和 USB IP 的 `reg base` 还有 `event_handler` 可缺省为NULL, `busid` 从 0 开始,不能超过 `CONFIG_USBHOST_MAX_BUS` +* 使用 `scons --target=mdk5` 或者 `scons` 进行编译,如果是mdk,需要使用 AC6 编译器 +* 链接脚本修改参考 :ref:`usbh_link_script` 章节 +* 如果芯片带 cache,cache 修改参考 :ref:`usb_cache` 章节 diff --git a/docs/zh/quick_start/share.rst b/docs/zh/quick_start/share.rst new file mode 100644 index 00000000..a57a8e1e --- /dev/null +++ b/docs/zh/quick_start/share.rst @@ -0,0 +1,27 @@ +开发者经验/开源项目分享 +======================== + +- `RT-Thread-CherryUSB - RT-Thread `_ + +- `[HPM-DIY]hpm6750 USB开源协议栈性能对比-cherryusb or tinyusb? `_ + +- `RT-Thread-CherryUSB移植笔记(一):APM32F407VGT6 DWC2移植 Port.A Full-Speed + Por.B High-SpeedRT-Thread问答社区 - RT-Thread `_ + +- `华大HC32F460XXX移植cherryusb协议栈,实现USB CDC ACM_cherryusb移植教程-CSDN博客 `_ + +- `rt-thread使用cherryusb实现虚拟串口-CSDN博客 `_ + +- `F1C100S+rtt+CherryUSB的USB HOST成功读到U盘 / 全志 SOC / WhyCan Forum(哇酷开发者社区) `_ + +- `模仿stm32标准库风格写的库文件(f1c100s/f1c200s),且已移植了rt-thread、lvgl、fatfs、cherryusb / 全志 SOC / WhyCan Forum(哇酷开发者社区) `_ + +- `printalyzer-timer: F-Stop enlarging timer and print exposure meter `_ + +- `MiSTeryNano: Atari STE MiSTery core for the Tang Nano 20k FPGA `_ + +- `Cherryuf2 `_ + +- `PicoPiFi: Driverless RNDIS USB WIFI Dongle `_ + +- `phobia: Phobia Motor Controller `_ + diff --git a/docs/zh/quick_start/start.rst b/docs/zh/quick_start/start.rst new file mode 100644 index 00000000..c6223b61 --- /dev/null +++ b/docs/zh/quick_start/start.rst @@ -0,0 +1,53 @@ +入门必看 +================== + +首先欢迎大家来到 usb 的世界,在这里你可以学习到 usb 各种知识以及 cherryusb 的移植使用进阶等等。但是呢,刚进来的你,一定很懵懂,因为 USB 很难(其实当你学会了 cherryusb以后,你会发现,USB 一点都不难), +那么这种情况下,你的学习路线,应该是怎么样呢?在这里,我推荐大家是按照我得学习路线来学习,这样对你的 USB 成长是最有帮助的,并且你也不会中途放弃。 + +首先,不允许上来就看概念,有句古诗说的好, **纸上得来终觉浅,绝知此事要躬行** ,光看纸面上的东西,你是学不到什么的,只有当自己实践了,你才能更深入的了解这些概念。那么作为初学者,你应该怎么做呢?请看以下步骤。 + + +第一步 +------------- + +你需要学过 C 语言,UART, DMA,这是基础,如果没学过,请去学习,不然你会很吃力。你会问 USB 跟 UART/DMA 有什么关系? 我只能说两个字, **等价** + +第二步 +------------- + +下载 demo 工程并跑通能运行, **建议学习慢的,使用 demo 同型号芯片**,学习快的,可以选择自己移植相关支持的型号的芯片。你连 demo 都跑不通,你学什么 USB,你说对不对? + +第三步 +--------- + +非常好,到这步,说明你已经能熟练移植和跑通所有示例了,那么接下来,你应该学习什么呢? **事务**, **请求** 和 **描述符** (在 USB 的学习过程中,你只需要知道这三个,其余都不需要知道)。 + +第四步 +---------- + +首先我们需要知道 USB 事务包含 SETUP/IN/OUT,其实就是等价于发送命令,发送数据和接收数据,很简单。至于下面枚举中你在外面的网络中所听到的控制阶段,数据阶段,状态阶段,他不是事务,他只是用多个事务代表了一个阶段而已。 + +第五步 +---------- + +然后你再去看 **USB 枚举** 章节并且知道了一个概念: **描述符** ,这个时候,你就可以去简单看看什么是描述符,有哪些描述符,然后你需要记住, **设备、配置、接口、端点描述符的组成**,并背下来,其余的你都不需要知道,因为其他都是固定的,后续都是 CV 。群文件有各类设备枚举的抓包,可以下下来看看。 + +第六步 +---------- + +然后呢,你可以再去看看什么是 **请求** ,请求结构体的组成,看看有哪些请求,简单了解即可,为什么呢?因为它不过就是 8 字节的数据格式,大家都会写一个 UART + 自定义协议,那么 USB 的请求也是一样的,只不过是规定好了而已。 + +第七步 +---------- + +这个时候,你该去熟悉下协议栈的一些 API 了,参考 **API 手册** 章节。并且你需要知道中断完成的条件是什么,什么时候算接收完成,什么时候算发送完成,可以参考 **USB 知识点拓展** 章节。 + +第八步 +---------- + +到这步呢,你肯定已经非常懂了,然后就可以开始你的一些小功能小项目了,在此期间呢,请循环查看 **USB 知识点拓展** 章节,直到你真的理解了,因为这些内容是非常重要的,会影响我们代码的执行结果。 + +第九步 +---------- + +都到这步了,你应该不需要我了,这个时候,你可以去看看 USB 概念,看看 USB 的一些细节,看看 CherryUSB 的代码流程了。然后就是巩固巩固再巩固了。恭喜你,出师了!!! diff --git a/docs/zh/quick_start/transplant.rst b/docs/zh/quick_start/transplant.rst new file mode 100644 index 00000000..710497d4 --- /dev/null +++ b/docs/zh/quick_start/transplant.rst @@ -0,0 +1,137 @@ +芯片通用移植指南 +========================= + +本节主要介绍所有带 USB IP 的芯片,移植 CherryUSB 主从协议栈时的通用步骤和注意事项。在移植之前,需要 **你准备好一个可以打印 helloworld 的基本工程** ,默认打印使用 `printf`, 如果是主机模式, **则需要准备好可以正常执行 os 调度的基本工程**。 + +USB Device 移植要点 +----------------------- + +- 拷贝 CherryUSB 源码到工程目录下,并按需添加源文件和头文件路径,头文件路径建议全部添加。其中 `usbd_core.c` 和 `usb_dc_xxx.c` 为必须添加项。而 `usb_dc_xxx.c` 是芯片所对应的 USB IP dcd 部分驱动,如果不知道自己芯片属于那个 USB IP,参考 **port** 目录下的不同 USB IP 的 readme。如果使用的 USB IP 没有支持,只能自己实现了 +- 拷贝 `cherryusb_config_template.h` 文件到自己工程目录下,命名为 `usb_config.h`,并添加相应的目录头文件路径 +- 实现 `usb_dc_low_level_init` 函数(该函数主要负责 USB 时钟、引脚、中断的初始化)。该函数可以放在你想要放的任何参与编译的 c 文件中。如何进行 USB 的时钟、引脚、中断等初始化,请自行根据你使用的芯片原厂提供的源码中进行添加。 +- 在中断函数中调用 `USBD_IRQHandler`,并传入 `busid`, 如果你的 SDK 中中断入口已经存在 `USBD_IRQHandler` ,请更改 USB 协议栈中的名称 +- 如果芯片带 cache,cache 修改参考 :ref:`usb_cache` 章节 +- 注册描述符并调用 `usbd_initialize`,填入 `busid` 和 USB IP 的 `reg base`, `busid` 从 0 开始,不能超过 `CONFIG_USBDEV_MAX_BUS`,可以直接使用 demo 下的 template + +USB Host 移植要点 +----------------------- + +- 拷贝 CherryUSB 源码到工程目录下,并按需添加源文件和头文件路径,头文件路径建议全部添加。其中 `usbh_core.c` 、 `usb_hc_xxx.c` 以及 **osal** 目录下源文件(根据不同的 os 选择对应的源文件)为必须添加项。而 `usb_hc_xxx.c` 是芯片所对应的 USB IP hcd 部分驱动,如果不知道自己芯片属于那个 USB IP,参考 **port** 目录下的不同 USB IP 的 readme。如果使用的 USB IP 没有支持,只能自己实现了 +- 拷贝 `cherryusb_config_template.h` 文件到自己工程目录下,命名为 `usb_config.h`,并添加相应的目录头文件路径 +- 实现 `usb_hc_low_level_init` 函数(该函数主要负责 USB 时钟、引脚、中断的初始化)。该函数可以放在你想要放的任何参与编译的 c 文件中。如何进行 USB 的时钟、引脚、中断等初始化,请自行根据你使用的芯片原厂提供的源码中进行添加。 +- 调用 `usbh_initialize` 并填入 `busid` 和 USB IP 的 `reg base` 还有 `event_handler` 可缺省为NULL, `busid` 从 0 开始,不能超过 `CONFIG_USBHOST_MAX_BUS` +- 在中断函数中调用 `USBH_IRQHandler`,并传入 `busid`, 如果你的 SDK 中中断入口已经存在 `USBH_IRQHandler` ,请更改 USB 协议栈中的名称 +- 链接脚本修改参考 :ref:`usbh_link_script` 章节 +- 如果芯片带 cache,cache 修改参考 :ref:`usb_cache` 章节 +- 调用 `usbh_initialize` ,填入 `busid` 和 USB IP 的 `reg base` 还有 `event_handler` 可缺省为NULL, `busid` 从 0 开始,不能超过 `CONFIG_USBHOST_MAX_BUS` 。基础的 cdc + hid + msc 参考 `usb_host.c` 文件,其余参考 **platform** 目录下适配 + +.. _usbh_link_script: + +主机链接脚本修改 +----------------------- + +在使用主机时,如果没有修改链接脚本,会报 `__usbh_class_info_start__` 和 `__usbh_class_info_end__` 未定义的错误。因为主机协议栈需要在链接脚本中添加一个 section 来存储 class 信息。 + +- 如果使用的是 KEIL 无需修改 + +- 如果使用的是 GCC ,需要在链接脚本中添加如下代码(需要放在 flash 位置,建议放最后): + +.. code-block:: C + + // 在 ld 文件中添加如下代码 + . = ALIGN(4); + __usbh_class_info_start__ = .; + KEEP(*(.usbh_class_info)) + __usbh_class_info_end__ = .; + +GCC 举例如下: + +.. code-block:: C + + /* The program code and other data into "FLASH" Rom type memory */ + .text : + { + . = ALIGN(4); + *(.text) /* .text sections (code) */ + *(.text*) /* .text* sections (code) */ + *(.glue_7) /* glue arm to thumb code */ + *(.glue_7t) /* glue thumb to arm code */ + *(.eh_frame) + + KEEP (*(.init)) + KEEP (*(.fini)) + . = ALIGN(4); + __usbh_class_info_start__ = .; + KEEP(*(.usbh_class_info)) + __usbh_class_info_end__ = .; + . = ALIGN(4); + _etext = .; /* define a global symbols at end of code */ + } > FLASH + +- Segger Embedded Studio 举例如下: + +.. code-block:: C + + define block cherryusb_usbh_class_info { section .usbh_class_info }; + + define exported symbol __usbh_class_info_start__ = start of block cherryusb_usbh_class_info; + define exported symbol __usbh_class_info_end__ = end of block cherryusb_usbh_class_info + 1; + + place in AXI_SRAM { block cherryusb_usbh_class_info }; + keep { section .usbh_class_info}; + + +.. _usb_cache: + +cache 配置修改 +------------------------------- + +对于带 cache 的芯片,协议栈以及 port 中不会对 cache 区域的 ram 进行 clean 或者 invalid,所以需要使用一块非 cache 区域的 ram 来维护。 +`USB_NOCACHE_RAM_SECTION` 宏表示将变量指定到非 cache ram上,默认 `USB_NOCACHE_RAM_SECTION` 定义为 `__attribute__((section(".noncacheable")))`。 +因此,用户需要在对应的链接脚本中添加 no cache ram 的 section,并且 section 段包含 `.noncacheable`。 + +.. note:: 需要注意,光修改链接脚本中的 nocache section 是不够的,还需要配置该 section 中的 ram 是真的 nocache,一般需要配置 mpu 属性(arm 的参考 stm32h7 demo)。 + +GCC: + +.. code-block:: C + + MEMORY + { + RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 256K - 64K + RAM_nocache (xrw) : ORIGIN = 0x20030000, LENGTH = 64K + FLASH (rx) : ORIGIN = 0x8000000, LENGTH = 512K + } + + ._nocache_ram : + { + . = ALIGN(4); + *(.noncacheable) + } >RAM_nocache + + +SCT: + +.. code-block:: C + + LR_IROM1 0x08000000 0x00200000 { ; load region size_region + ER_IROM1 0x08000000 0x00200000 { ; load address = execution address + *.o (RESET, +First) + *(InRoot$$Sections) + .ANY (+RO) + .ANY (+XO) + } + RW_IRAM2 0x24000000 0x00070000 { ; RW data + .ANY (+RW +ZI) + } + USB_NOCACHERAM 0x24070000 0x00010000 { ; RW data + *(.noncacheable) + } + } + +ICF: + +.. code-block:: C + + define region NONCACHEABLE_RAM = [from 0x1140000 size 256K]; + place in NONCACHEABLE_RAM { section .noncacheable, section .noncacheable.init, section .noncacheable.bss }; // Noncacheable diff --git a/docs/zh/show/img/usbdev_msc.png b/docs/zh/show/img/usbdev_msc.png new file mode 100644 index 00000000..30f22383 Binary files /dev/null and b/docs/zh/show/img/usbdev_msc.png differ diff --git a/docs/zh/show/img/usbdev_rndis_linux.png b/docs/zh/show/img/usbdev_rndis_linux.png new file mode 100644 index 00000000..94b97312 Binary files /dev/null and b/docs/zh/show/img/usbdev_rndis_linux.png differ diff --git a/docs/zh/show/img/usbdev_rndis_lwip.png b/docs/zh/show/img/usbdev_rndis_lwip.png new file mode 100644 index 00000000..f4cfd0b3 Binary files /dev/null and b/docs/zh/show/img/usbdev_rndis_lwip.png differ diff --git a/docs/zh/show/img/usbdev_rndis_lwip2.png b/docs/zh/show/img/usbdev_rndis_lwip2.png new file mode 100644 index 00000000..3fde91f9 Binary files /dev/null and b/docs/zh/show/img/usbdev_rndis_lwip2.png differ diff --git a/docs/zh/show/img/usbdev_rndis_wifi.png b/docs/zh/show/img/usbdev_rndis_wifi.png new file mode 100644 index 00000000..d6817876 Binary files /dev/null and b/docs/zh/show/img/usbdev_rndis_wifi.png differ diff --git a/docs/zh/show/img/usbdev_rndis_wifi2.png b/docs/zh/show/img/usbdev_rndis_wifi2.png new file mode 100644 index 00000000..dba9f3dd Binary files /dev/null and b/docs/zh/show/img/usbdev_rndis_wifi2.png differ diff --git a/docs/zh/show/img/usbdev_rndis_win.png b/docs/zh/show/img/usbdev_rndis_win.png new file mode 100644 index 00000000..5293023a Binary files /dev/null and b/docs/zh/show/img/usbdev_rndis_win.png differ diff --git a/docs/zh/show/img/usbdev_uvc_mjpeg.png b/docs/zh/show/img/usbdev_uvc_mjpeg.png new file mode 100644 index 00000000..a2321c15 Binary files /dev/null and b/docs/zh/show/img/usbdev_uvc_mjpeg.png differ diff --git a/docs/zh/show/img/usbdev_uvc_yuv.png b/docs/zh/show/img/usbdev_uvc_yuv.png new file mode 100644 index 00000000..a630cd67 Binary files /dev/null and b/docs/zh/show/img/usbdev_uvc_yuv.png differ diff --git a/docs/zh/show/img/usbhost_ax88772_1.png b/docs/zh/show/img/usbhost_ax88772_1.png new file mode 100644 index 00000000..a267b292 Binary files /dev/null and b/docs/zh/show/img/usbhost_ax88772_1.png differ diff --git a/docs/zh/show/img/usbhost_ax88772_2.png b/docs/zh/show/img/usbhost_ax88772_2.png new file mode 100644 index 00000000..fc6e96fc Binary files /dev/null and b/docs/zh/show/img/usbhost_ax88772_2.png differ diff --git a/docs/zh/show/img/usbhost_hub.png b/docs/zh/show/img/usbhost_hub.png new file mode 100644 index 00000000..011468c7 Binary files /dev/null and b/docs/zh/show/img/usbhost_hub.png differ diff --git a/docs/zh/show/img/usbhost_hub2.png b/docs/zh/show/img/usbhost_hub2.png new file mode 100644 index 00000000..00c09d6f Binary files /dev/null and b/docs/zh/show/img/usbhost_hub2.png differ diff --git a/docs/zh/show/img/usbhost_msc.png b/docs/zh/show/img/usbhost_msc.png new file mode 100644 index 00000000..ec546a8d Binary files /dev/null and b/docs/zh/show/img/usbhost_msc.png differ diff --git a/docs/zh/show/img/usbhost_msc_xhci.png b/docs/zh/show/img/usbhost_msc_xhci.png new file mode 100644 index 00000000..084250f2 Binary files /dev/null and b/docs/zh/show/img/usbhost_msc_xhci.png differ diff --git a/docs/zh/show/img/usbhost_rndis.png b/docs/zh/show/img/usbhost_rndis.png new file mode 100644 index 00000000..12ab1a4e Binary files /dev/null and b/docs/zh/show/img/usbhost_rndis.png differ diff --git a/docs/zh/show/img/usbhost_uvc.gif b/docs/zh/show/img/usbhost_uvc.gif new file mode 100644 index 00000000..c4df04e0 Binary files /dev/null and b/docs/zh/show/img/usbhost_uvc.gif differ diff --git a/docs/zh/show/img/usbhost_wifi.png b/docs/zh/show/img/usbhost_wifi.png new file mode 100644 index 00000000..e57fd85b Binary files /dev/null and b/docs/zh/show/img/usbhost_wifi.png differ diff --git a/docs/zh/show/index.rst b/docs/zh/show/index.rst new file mode 100644 index 00000000..c5d3f708 --- /dev/null +++ b/docs/zh/show/index.rst @@ -0,0 +1,103 @@ +.. _performace_show: + +性能展示 +============================== + +以下演示了 CherryUSB 在不同应用中的性能表现。主要演示高速模式,全速看不出什么性能差异。 + +CDC ACM 通信 +---------------- + +可以达到硬件极限性能,当然需要硬件理论支持到这速度,CherryUSB 就支持到这速度,举例如下: + +- HPM 系列(从机可以到 42MB/S, 主机 44MB/S, 已经达到硬件极限) +- BL 系列(从机 32MB/S, 主机 25MB/S, 已经达到硬件极限) +- STM32F4 全速(从机 900KB/S, 主机 1.12MB/S, 已经达到硬件极限) + +从机测速demo: cdc_acm_template.c 并且关闭 log,脚本使用 `tools/test_srcipts/test_cdc_speed.py` +主机测速demo: usb_host.c 中 TEST_USBH_CDC_SPEED=1 + +USB Device MSC +----------------- + +演示 USB Device MSC 使用 SDXC3.0 + EMMC 测试。 + +.. figure:: img/usbdev_msc.png + +USB Device RNDIS +----------------------- + +.. note:: 默认 rndis 仅支持单包,因此下面速度为最低速度。多包支持需要联系作者。 + +演示 USB Device RNDIS 局域网下搭配 lwip 的速度。 + +作为 client + +.. figure:: img/usbdev_rndis_lwip.png + +作为 server + +.. figure:: img/usbdev_rndis_lwip2.png + +演示 USB Device RNDIS + WIFI 透传测试。 + +.. figure:: img/usbdev_rndis_wifi.png +.. figure:: img/usbdev_rndis_wifi2.png + +演示 USB Device RNDIS + 百兆以太网透传测试。 + +.. figure:: img/usbdev_rndis_win.png +.. figure:: img/usbdev_rndis_linux.png + +USB Device UVC +----------------------- + +演示 USB Device UVC + 摄像头传输 YUYV/MJPEG 640 * 480 图像。FPS 30。 + +.. figure:: img/usbdev_uvc_mjpeg.png +.. figure:: img/usbdev_uvc_yuv.png + +USB Host HUB +----------------------- + +多级 hub 支持,演示 1托 7 HUB + +.. figure:: img/usbhost_hub.png +.. figure:: img/usbhost_hub2.png + +USB Host MSC +----------------------- + +演示 USB Host MSC 在 USB2.0 和 USB3.0 下的速度,U盘推荐使用固态测试。 + +.. figure:: img/usbhost_msc.png +.. figure:: img/usbhost_msc_xhci.png + +USB Host UVC +----------------------- + +演示 USB Host UVC 驱动 648 * 480 YUV 摄像头。FPS 30。 + +.. figure:: img/usbhost_uvc.gif + +USB Host ASIX 网卡 +----------------------- + +演示 USB Host 驱动 AX88772 USB 以太网模块。 + +.. figure:: img/usbhost_ax88772_1.png +.. figure:: img/usbhost_ax88772_2.png + +USB Host RNDIS 网卡 +----------------------- + +演示 USB Host 驱动手机,手机开启 USB 共享网络即可使用 RNDIS 。 + +.. figure:: img/usbhost_rndis.png + +USB Host WIFI +----------------------- + +演示 USB Host 驱动 BL616 USB WIFI。 + +.. figure:: img/usbhost_wifi.png diff --git a/docs/zh/support/img/dwc2_hostuac.png b/docs/zh/support/img/dwc2_hostuac.png new file mode 100644 index 00000000..6050f531 Binary files /dev/null and b/docs/zh/support/img/dwc2_hostuac.png differ diff --git a/docs/zh/support/img/dwc2_hostuvc1.png b/docs/zh/support/img/dwc2_hostuvc1.png new file mode 100644 index 00000000..70b4dd1a Binary files /dev/null and b/docs/zh/support/img/dwc2_hostuvc1.png differ diff --git a/docs/zh/support/img/dwc2_hostuvc2.png b/docs/zh/support/img/dwc2_hostuvc2.png new file mode 100644 index 00000000..8885e90e Binary files /dev/null and b/docs/zh/support/img/dwc2_hostuvc2.png differ diff --git a/docs/zh/support/img/dwc2_hostuvc3.png b/docs/zh/support/img/dwc2_hostuvc3.png new file mode 100644 index 00000000..fb3e1eef Binary files /dev/null and b/docs/zh/support/img/dwc2_hostuvc3.png differ diff --git a/docs/zh/support/img/ehci_hostuvc1.png b/docs/zh/support/img/ehci_hostuvc1.png new file mode 100644 index 00000000..2bd6590a Binary files /dev/null and b/docs/zh/support/img/ehci_hostuvc1.png differ diff --git a/docs/zh/support/img/ehci_hostuvc2.png b/docs/zh/support/img/ehci_hostuvc2.png new file mode 100644 index 00000000..f44fa68c Binary files /dev/null and b/docs/zh/support/img/ehci_hostuvc2.png differ diff --git a/docs/zh/support/img/mtpdev.png b/docs/zh/support/img/mtpdev.png new file mode 100644 index 00000000..513b8ac9 Binary files /dev/null and b/docs/zh/support/img/mtpdev.png differ diff --git a/docs/zh/support/img/ohci.png b/docs/zh/support/img/ohci.png new file mode 100644 index 00000000..171f77be Binary files /dev/null and b/docs/zh/support/img/ohci.png differ diff --git a/docs/zh/support/img/rndisrx.png b/docs/zh/support/img/rndisrx.png new file mode 100644 index 00000000..ce1133ed Binary files /dev/null and b/docs/zh/support/img/rndisrx.png differ diff --git a/docs/zh/support/img/rndistx.png b/docs/zh/support/img/rndistx.png new file mode 100644 index 00000000..69e45db8 Binary files /dev/null and b/docs/zh/support/img/rndistx.png differ diff --git a/docs/zh/support/img/tmcdev1.png b/docs/zh/support/img/tmcdev1.png new file mode 100644 index 00000000..1eaf7155 Binary files /dev/null and b/docs/zh/support/img/tmcdev1.png differ diff --git a/docs/zh/support/img/tmcdev2.png b/docs/zh/support/img/tmcdev2.png new file mode 100644 index 00000000..97c8297b Binary files /dev/null and b/docs/zh/support/img/tmcdev2.png differ diff --git a/docs/zh/support/img/usbhost_uvc.gif b/docs/zh/support/img/usbhost_uvc.gif new file mode 100644 index 00000000..c4df04e0 Binary files /dev/null and b/docs/zh/support/img/usbhost_uvc.gif differ diff --git a/docs/zh/support/index.rst b/docs/zh/support/index.rst new file mode 100644 index 00000000..e30c4bb0 --- /dev/null +++ b/docs/zh/support/index.rst @@ -0,0 +1,43 @@ +商业支持 +============================== + +以下内容为商业收费类,如需支持,请邮件到 1203593632@qq.com。 + +- OHCI 驱动 + +.. figure:: img/ohci.png + +- EHCI IP 中 ISO 驱动和 UAC/UVC 框架,搭配主机 UVC & UAC 类(这部分是开源的)使用。iso 支持一个微帧 1/2/3 包,支持 MJPEG 和 YUV 摄像头 + +.. figure:: img/ehci_hostuvc1.png +.. figure:: img/ehci_hostuvc2.png + +演示 USB Host UVC 驱动 648 * 480 YUV 摄像头。FPS 30。 + +.. figure:: img/usbhost_uvc.gif + +- DWC2 IP 中 ISO 驱动和 UAC/UVC 框架,搭配主机 UVC & UAC 类(这部分是开源的)使用。iso 支持一个微帧 1/2/3 包,支持 MJPEG 和 YUV 摄像头 + +.. figure:: img/dwc2_hostuvc1.png +.. figure:: img/dwc2_hostuvc2.png +.. figure:: img/dwc2_hostuvc3.png +.. figure:: img/dwc2_hostuac.png + +- MUSB IP 中 ISO 驱动和 UAC/UVC 框架,搭配主机 UVC & UAC 类(这部分是开源的)使用。MUSB 需要为 mentor 公司制定的标准 IP + +- 从机 MTP 类驱动, 支持多文件和多文件夹,支持 MCU 端增删文件并与 PC 同步 + +.. figure:: img/mtpdev.png + +- 从机 TMC 类驱动 + +.. figure:: img/tmcdev1.png +.. figure:: img/tmcdev2.png + +- USB 网卡类高性能版本优化,包含 CDC-NCM, CDC-RNDIS, 私有类驱动(支持多包发送和接收),下面举例 RNDIS + +.. figure:: img/rndistx.png +.. figure:: img/rndisrx.png + +- 定制化 class 驱动或者 IP 驱动适配 +- 技术支持相关 \ No newline at end of file diff --git a/docs/zh/tools/img/chrytool1.png b/docs/zh/tools/img/chrytool1.png new file mode 100644 index 00000000..8717316a Binary files /dev/null and b/docs/zh/tools/img/chrytool1.png differ diff --git a/docs/zh/tools/img/chrytool2.png b/docs/zh/tools/img/chrytool2.png new file mode 100644 index 00000000..a0eb4192 Binary files /dev/null and b/docs/zh/tools/img/chrytool2.png differ diff --git a/docs/zh/tools/img/chrytool3.png b/docs/zh/tools/img/chrytool3.png new file mode 100644 index 00000000..52a3556b Binary files /dev/null and b/docs/zh/tools/img/chrytool3.png differ diff --git a/docs/zh/tools/img/chrytool4.png b/docs/zh/tools/img/chrytool4.png new file mode 100644 index 00000000..8ad68400 Binary files /dev/null and b/docs/zh/tools/img/chrytool4.png differ diff --git a/docs/zh/tools/img/chrytool5.png b/docs/zh/tools/img/chrytool5.png new file mode 100644 index 00000000..17849324 Binary files /dev/null and b/docs/zh/tools/img/chrytool5.png differ diff --git a/docs/zh/tools/img/chrytool6.png b/docs/zh/tools/img/chrytool6.png new file mode 100644 index 00000000..931ccad8 Binary files /dev/null and b/docs/zh/tools/img/chrytool6.png differ diff --git a/docs/zh/tools/img/chrytool7.png b/docs/zh/tools/img/chrytool7.png new file mode 100644 index 00000000..283a7fc9 Binary files /dev/null and b/docs/zh/tools/img/chrytool7.png differ diff --git a/docs/zh/tools/index.rst b/docs/zh/tools/index.rst new file mode 100644 index 00000000..0ebfb31d --- /dev/null +++ b/docs/zh/tools/index.rst @@ -0,0 +1,50 @@ +chryusb_configurator +-------------------------- + +`chryusb_configurator `_ 主要服务在使用设备协议栈时,生成描述符数组,从而调用 `usbd_desc_register` 进行注册。 + +- 首先我们从 github 下载 chryusb_configurator.exe,然后一路安装就可以了。然后双击打开,点击 `工程`,并点击 `新建工程` + +.. figure:: img/chrytool1.png + +- 新建完成以后,会生成默认的描述符配置,包含 **设备描述符**、 **配置描述符**、 **字符串描述符**,并且 **字符串描述符** 默认支持三个 + +.. figure:: img/chrytool2.png + +- 然后我们可以根据需要修改相关描述符的信息,比如 **设备描述符** 中的 vid、pid,class 参数, **配置描述符** 中的 **Power** 等等 + +- 然后是 class 的添加,需要点击 `文件`,并点击 `新建文件` + +.. figure:: img/chrytool3.png + +- 然后右侧提供了一些 class 的描述符模板,选择一个进行初始化 + +.. figure:: img/chrytool4.png + +- 如果是多个 class ,则上述两步重复操作就可以了 + +- 然后我们根据需要修改相关端点的参数,比如方向、地址、size、interval + +.. figure:: img/chrytool5.png + +- 最后点击 `文件` 并保存文件,后缀为 `.chry` +- 切换到工程文件,后缀是 `.chrybase`, 然后点击 `添加分组配置` 导入刚刚配置好的 class 文件 + +.. figure:: img/chrytool6.png + +- 点击 `工程` 并点击 `保存工程` +- 点击 `编译`,生成描述符数组 + +.. figure:: img/chrytool7.png + +- 复制编译后的文件到自己的工程中使用即可 + + +力科 USB Protocol Suite +-------------------------- + +Wireshark +-------------------------- + +Audacity +-------------------------- diff --git a/docs/zh/usb/img/1.png b/docs/zh/usb/img/1.png new file mode 100644 index 00000000..e85ddf7a Binary files /dev/null and b/docs/zh/usb/img/1.png differ diff --git a/docs/zh/usb/img/10.png b/docs/zh/usb/img/10.png new file mode 100644 index 00000000..bb57645e Binary files /dev/null and b/docs/zh/usb/img/10.png differ diff --git a/docs/zh/usb/img/11.png b/docs/zh/usb/img/11.png new file mode 100644 index 00000000..11056e33 Binary files /dev/null and b/docs/zh/usb/img/11.png differ diff --git a/docs/zh/usb/img/12.png b/docs/zh/usb/img/12.png new file mode 100644 index 00000000..4149d81e Binary files /dev/null and b/docs/zh/usb/img/12.png differ diff --git a/docs/zh/usb/img/13.png b/docs/zh/usb/img/13.png new file mode 100644 index 00000000..29a544b2 Binary files /dev/null and b/docs/zh/usb/img/13.png differ diff --git a/docs/zh/usb/img/14.png b/docs/zh/usb/img/14.png new file mode 100644 index 00000000..8ca094a4 Binary files /dev/null and b/docs/zh/usb/img/14.png differ diff --git a/docs/zh/usb/img/15.png b/docs/zh/usb/img/15.png new file mode 100644 index 00000000..eba7b89b Binary files /dev/null and b/docs/zh/usb/img/15.png differ diff --git a/docs/zh/usb/img/16.png b/docs/zh/usb/img/16.png new file mode 100644 index 00000000..259336ca Binary files /dev/null and b/docs/zh/usb/img/16.png differ diff --git a/docs/zh/usb/img/17.png b/docs/zh/usb/img/17.png new file mode 100644 index 00000000..c42de390 Binary files /dev/null and b/docs/zh/usb/img/17.png differ diff --git a/docs/zh/usb/img/18.png b/docs/zh/usb/img/18.png new file mode 100644 index 00000000..f08b6354 Binary files /dev/null and b/docs/zh/usb/img/18.png differ diff --git a/docs/zh/usb/img/19.png b/docs/zh/usb/img/19.png new file mode 100644 index 00000000..2e6eb9ce Binary files /dev/null and b/docs/zh/usb/img/19.png differ diff --git a/docs/zh/usb/img/2.png b/docs/zh/usb/img/2.png new file mode 100644 index 00000000..5b4f5f20 Binary files /dev/null and b/docs/zh/usb/img/2.png differ diff --git a/docs/zh/usb/img/20.png b/docs/zh/usb/img/20.png new file mode 100644 index 00000000..a44898a8 Binary files /dev/null and b/docs/zh/usb/img/20.png differ diff --git a/docs/zh/usb/img/21.png b/docs/zh/usb/img/21.png new file mode 100644 index 00000000..7aa81e95 Binary files /dev/null and b/docs/zh/usb/img/21.png differ diff --git a/docs/zh/usb/img/22.png b/docs/zh/usb/img/22.png new file mode 100644 index 00000000..370d39f9 Binary files /dev/null and b/docs/zh/usb/img/22.png differ diff --git a/docs/zh/usb/img/23.png b/docs/zh/usb/img/23.png new file mode 100644 index 00000000..e08db16e Binary files /dev/null and b/docs/zh/usb/img/23.png differ diff --git a/docs/zh/usb/img/24.png b/docs/zh/usb/img/24.png new file mode 100644 index 00000000..fec98d49 Binary files /dev/null and b/docs/zh/usb/img/24.png differ diff --git a/docs/zh/usb/img/25.png b/docs/zh/usb/img/25.png new file mode 100644 index 00000000..9bcaf151 Binary files /dev/null and b/docs/zh/usb/img/25.png differ diff --git a/docs/zh/usb/img/26.png b/docs/zh/usb/img/26.png new file mode 100644 index 00000000..d439b7c4 Binary files /dev/null and b/docs/zh/usb/img/26.png differ diff --git a/docs/zh/usb/img/27.png b/docs/zh/usb/img/27.png new file mode 100644 index 00000000..1047da1b Binary files /dev/null and b/docs/zh/usb/img/27.png differ diff --git a/docs/zh/usb/img/28.png b/docs/zh/usb/img/28.png new file mode 100644 index 00000000..95b760c5 Binary files /dev/null and b/docs/zh/usb/img/28.png differ diff --git a/docs/zh/usb/img/29.png b/docs/zh/usb/img/29.png new file mode 100644 index 00000000..09538d16 Binary files /dev/null and b/docs/zh/usb/img/29.png differ diff --git a/docs/zh/usb/img/3.png b/docs/zh/usb/img/3.png new file mode 100644 index 00000000..b8ef0823 Binary files /dev/null and b/docs/zh/usb/img/3.png differ diff --git a/docs/zh/usb/img/30.png b/docs/zh/usb/img/30.png new file mode 100644 index 00000000..d3014f95 Binary files /dev/null and b/docs/zh/usb/img/30.png differ diff --git a/docs/zh/usb/img/4.png b/docs/zh/usb/img/4.png new file mode 100644 index 00000000..f80c5366 Binary files /dev/null and b/docs/zh/usb/img/4.png differ diff --git a/docs/zh/usb/img/5.png b/docs/zh/usb/img/5.png new file mode 100644 index 00000000..ec6a4ba2 Binary files /dev/null and b/docs/zh/usb/img/5.png differ diff --git a/docs/zh/usb/img/6.png b/docs/zh/usb/img/6.png new file mode 100644 index 00000000..2d280398 Binary files /dev/null and b/docs/zh/usb/img/6.png differ diff --git a/docs/zh/usb/img/7.png b/docs/zh/usb/img/7.png new file mode 100644 index 00000000..e7562f11 Binary files /dev/null and b/docs/zh/usb/img/7.png differ diff --git a/docs/zh/usb/img/8.png b/docs/zh/usb/img/8.png new file mode 100644 index 00000000..a4ac6ad4 Binary files /dev/null and b/docs/zh/usb/img/8.png differ diff --git a/docs/zh/usb/img/9.png b/docs/zh/usb/img/9.png new file mode 100644 index 00000000..a8b5b2a3 Binary files /dev/null and b/docs/zh/usb/img/9.png differ diff --git a/docs/zh/usb/img/overview1.png b/docs/zh/usb/img/overview1.png new file mode 100644 index 00000000..fbaf5a19 Binary files /dev/null and b/docs/zh/usb/img/overview1.png differ diff --git a/docs/zh/usb/img/overview2.png b/docs/zh/usb/img/overview2.png new file mode 100644 index 00000000..c8b3b779 Binary files /dev/null and b/docs/zh/usb/img/overview2.png differ diff --git a/docs/zh/usb/img/usb_enum.png b/docs/zh/usb/img/usb_enum.png new file mode 100644 index 00000000..01c67c15 Binary files /dev/null and b/docs/zh/usb/img/usb_enum.png differ diff --git a/docs/zh/usb/img/usb_request.png b/docs/zh/usb/img/usb_request.png new file mode 100644 index 00000000..bb9f2637 Binary files /dev/null and b/docs/zh/usb/img/usb_request.png differ diff --git a/docs/zh/usb/img/usbstruct.png b/docs/zh/usb/img/usbstruct.png new file mode 100644 index 00000000..bd062ca3 Binary files /dev/null and b/docs/zh/usb/img/usbstruct.png differ diff --git a/docs/zh/usb/usb2.0_basic.rst b/docs/zh/usb/usb2.0_basic.rst new file mode 100644 index 00000000..1c2b599e --- /dev/null +++ b/docs/zh/usb/usb2.0_basic.rst @@ -0,0 +1,296 @@ +USB 基本概念(2.0 为主) +=========================== + +本文主要对 USB 官方手册 `usb2.0.pdf `_ 中提供的第五章、第七章、第八章、第九章进行讲解。 +如果是初学 usb 的同学,推荐先不要看本节,而是将示例 demo 能够跑通了,熟悉了使用,再来看。 + +简介 +--------- + +USB 是什么?干什么用的?有什么优点?这些大家可以百度,我就不提了。主要先说 USB 的接口和速度根据不同的 USB 版本的分类,如图所示: + +.. figure:: img/overview1.png + +其次是 USB 需要满足的电平标准,有了电平标准后,下面说的信号状态就可以进行分类了。USB2.0 和 USB3.0 支持的电压范围和最大电流如下: + +.. figure:: img/overview2.png + +USB 信号状态 +----------------- + +首先我们需要了解的是 USB 的电气特性中的 Signaling Level,也就是信号状态。USB 主要是靠 D+ 和 D- 来实现不同的信号状态,然后进行通信。官方手册 7.1.7 中列举出了低速、全速和高速时的信号状态对应的 D+ 和 D- 需要满足的要求。 + +.. figure:: img/1.png +.. figure:: img/2.png +.. figure:: img/3.png + +- **差分 0 和差分 1**: 这两个状态用于通过 USB 进行的通用数据通信。当 D+线为高电平、 D-线为低电平时,该状态为差分 1。当 D+线为低电平、 D-线为高电平时,该状态为差分 0。 +- **J 状态和 K 状态**: 除了差分信号外, USB 规范还定义了其他两个差分状态: J 状态和 K 状态。它们的定义由设备速度决定。在全速和高速设备上, J 状态为差分 1 而 K 状态是差分 0。在低速设备上,该情况则相反。 +- **单端 0( SE0)**: 在 D+和 D-均为低电平时所发生的状态。该状态表示一个复位、断连或数据包的结束。 +- **单端 1( SE1)**: 在 D+和 D-均为高电平时发生的状态。不会故意生成该状态,并且不能在 USB 设计中出现。 +- **闲置**: 必须在发送一个数据包的前后发生的状态。如果一个数据线为低电平,而另一个数据线为高电平,则表示闲置状态。高电平和低电平的定义由设备的速度决定。在全速设备上,闲置状态是指 D+为高电平、 D-为低电平。在低速设备上,该情况则相反。 +- **恢复**: 用于使设备从挂起状态唤醒。通过发送一个 K 状态实现该操作。 +- **数据包的开始( SOP)**: 当 D+和 D-线从闲置状态转换到 K 状态时,将在开始低速或全速数据包前发生。 +- **数据包的结束( EOP)**: 在低速或全速数据包结束时发生。当 SE0 状态持续两位时间(后面的内容将介绍位时间)以及 J 状态持续 1 位时间时,将发生 EOP。 +- **复位**: 在 SE0 状态持续 10 ms 时发生。在 SE0 至少持续 2.5 ms 后,该设备会复位,并开始进入复位状态。 +- **保持活动( Keep Alive)**: 在低速设备中使用的信号。低速设备缺少了一个帧起始数据包(用于防止挂起状态)。每次经过 1 ms,它们都会使用一个 EOP 来防止设备进入挂起状态。 + +.. note::这里需要注意的一点就是, J K状态和差分0/1,对于低速来说,和全速/高速是相反的。 + +下面我们通过一个波形,来区分这些信号状态: + +.. figure:: img/4.png + +- 第一个红框,可以看出是一个数据包的开始,并且假设这是一个全速设备,那么D+ 为高,D- 为低,是一个闲置状态。 +- 第二个红框,D+为低,D- 为高,说明是一个 K 状态,由 闲置转 K 状态说明他是一个 SOP。 +- 第三个红框开始表示数据,表示 JKJKJKJKJK。 +- 第四个红框表示 SE0 ,因为D+和 D-均为低电平。 +- 第五个红框,而 SE0 持续了一段时间后,变成了 D+高,D- 低,说明他是一个 J 状态,从 SE0 切换成 J 状态,说明他是一个 EOP。 + +USB 速度识别 +--------------------- + +USB 的速度是如何判定的? 这个见手册 7.1.5.1。USB 的速度检测主要是靠 D+ 和 D-线上拉 1.5K决定,如果 D+上拉1.5k,则该设备为全速设备,如果 D-上拉1.5k,则为低速设备。而高速设备初始是以一个全速设备的身份出现,和全速设备一样,D+线上有一个1.5k的上拉电阻。USB2.0的hub把它当作一个全速设备,之后,hub 和设备通过一系列握手信号确认双方的身份,最终判定该设备为高速设备。 + +.. figure:: img/5.png + +USB 连接与断开检测 +--------------------- + +那么 当我们的设备插上 USB 主机时,主机是如何知道有设备插入或者拔出呢?手册 7.1.7.3 给出了答案,如图所示: + +.. figure:: img/6.png +.. figure:: img/7.png + +首先是连接检测,主机检测到某一个数据线电平拉高保持了一段时间,就认为有设备连接上来了。低速设备连接时,主机会检测到D-线被拉高,全速/高速设备连接时,主机会检测到D+线被拉高。 +而断开检测,则是主机端D+、D-数据线上的下拉电阻起作用,断开后使得二者都在低电平;当低电平持续 TDDIS 时间就会被主机认为是断开状态。上图中,TDDIS在2到2.5us之间。 + +USB 电源 +--------------------- + +作为 USB 电源时, USB 设备可被划分为两种设备类型:总线供电和自供电。 + +- 总线供电是 USB 设计的一个优势。由于设备通过总线供电,因此不需要使用笨重的内部或外部电源,它仍能够维持自身操作。总线可由主机或集线器供电。使用某个总线供电的设备时,用户将设备配置为某种状态前必须考虑其功耗。 +- 自供电设备通过使用外部电源(如直流电源适配器或电池)为自己供电。自供电设备在进行设计的过程中需要考虑到一些注意事项。 USB 规范要求自供电设备一直监控自己的 VBUS 线。 VBUS 不存在的时间内,设备必须断开提供给 D+/D-线上的上拉电阻的电源,从而防止向主机或集线器供电。 否则,会导致 USB 合规性测试发生失败。但是自供电集线器能够从总线获得最多 100 mA 的电流。 + +USB 设备状态 +--------------------- + +在 USB 插上主机的那一刻, USB 设备本身的设备状态是会变化的。而这个设备状态,后面如果学习到枚举过程,可以知道,其实这段变化描述的就是枚举过程。这部分见手册 9.1.1。 + +.. figure:: img/9.png + +- 连接状态: 当将某个设备插入到主机/集线器,但主机/集线器不给 VBUS 线供电时,会出现这种状态。它通常在集线器检测到一个过流事件时出现。虽然仍连接着设备,但主机移除了供给它的电源。 +- 供电: 某个设备被连接到 USB 上并得到供电,但仍未接收到一个复位请求。 +- 默认: 某个设备被连接到 USB 上、得到供电,并且由主机进行了复位。这时,设备没有任何设备地址。 设备会响应地址 0。 +- 地址: 某个设备被连接到 USB、得到供电、被复位,并且有一个唯一的地址。但是设备仍未得到配置。 +- 配置: 设备已经连接到 USB、得到供电、被复位、具有唯一的地址、得到配置,但尚未进入挂起状态。此时,总线供电设备能够消耗超过 100 mA 的电流。 +- 挂起: 如上面所述,设备已经建立好了连接,并且得到配置,但在 3 ms 时间内不会进行任意总线操作。 + +翻译成中文图就是: + +.. figure:: img/10.png + +USB 编码与位填充 +--------------------- + +首先,USB 的数据是串行发送的,就像 UART、I2C、SPI 等等,连续的01 信号只通过一根数据线发送给接受者。但是因为发送者和接收者运行的频率不一样,信号的同步就是个问题,比如,接受者接收到了一个持续一段时间的低电平,无法得知这究竟是代表了 5 个 0 还是 1000 个 0。一个解决办法,就是在传输数据信号的同时,附加一个时钟信号,用来同步两端的传输,接受者在时钟信号的辅助下对数据信号采样,就可以正确解析出发送的数据了,比如 I2C 就是这样做的,SDA 来传输数据,SCL 来传输同步时钟: + +.. figure:: img/11.png + +虽然这样解决了问题,但是却需要附加一根时钟信号线来传输时钟。因为USB没有时钟信号,有没有不需要附加的时钟信号,也能保持两端的同步呢? +有的,这就是 RZ 编码(Return-to-zero Code),也叫做归零编码。 + +RZ 编码(Return-to-zero Code) +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +RZ 编码(Return-to-zero Code),也叫做归零编码。在 RZ 编码中,正电平代表逻辑 1,负电平代表逻辑 0,并且,每传输完一位数据,信号返回到零电平,也就是说,信号线上会出现 3 种电平:正电平、负电平、零电平。 + +.. figure:: img/12.png + +从图上就可以看出来,因为每位传输之后都要归零,所以接受者只要在信号归零后采样即可,这样就不在需要单独的时钟信号。实际上, RZ 编码就是相当于把时钟信号用归零编码在了数据之内。这样的信号也叫做自同步(self-clocking)信号。 +这样虽然省了时钟数据线,但是还是有缺点的,因为在 RZ 编码中,大部分的数据带宽,都用来传输“归零”而浪费掉了。 + +NRZ 编码(Non-return-to-zero Code) +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +去掉这个归零步骤,NRZ 编码(Non-return-to-zero Code)就出现了,和 RZ 的区别就是 NRZ 是不需要归零的。 + +.. figure:: img/13.png + +NRZI 编码(Non-Return-to-Zero Inverted Code) +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +NRZI 编码(Non-Return-to-Zero Inverted Code)和 NRZ 的区别就是 NRZI 用信号的翻转代表一个逻辑,信号保持不变代表另外一个逻辑。这个见手册 7.1.8。 + +.. figure:: img/14.png + +如图所示,可以得出一个简单的记忆方式:遇到 0 的边沿电平就翻转,遇到 1 的边沿则不变。 + +位填充(bit-stuffing) +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +但是,这样还是会有一个问题,就是虽然接受者可以主动和发送者的频率匹配,但是两者之间总会有误差。假如数据信号是 1000 个逻辑 1,经过 USB 的 NRZI 编码之后,就是很长一段没有变化的电平,在这种情况下,即使接受者的频率和发送者相差千分之一,就会造成把数据采样成 1001 个或者 999 个 1了。 +USB 对这个问题的解决办法,就是强制插 0,也就是(位填充)bit-stuffing,如果要传输的数据中有 6个连续的 1,发送前就会在第 6 个 1 后面强制插入一个 0,让发送的信号强制出现翻转,从而强制接受者进行频率调整。 +接受者只要删除 6 个连续 1 之后的 0,就可以恢复原始的数据了。这部分见手册 7.1.9。 + +.. figure:: img/15.png +.. figure:: img/16.png +.. figure:: img/17.png + +在数据被NRZI编码之前,在数据流中每六个连续的1之后插入一个0,以强制NRZI数据流中的过渡,这使接收器逻辑至少每七位有一次数据转换,以保证数据和时钟的锁定。比特填充是从同步模式开始启用。结束同步模式的数据 "一 "被算作是序列中的第一个 "一"。序列中的第一个。除了高速EOP期间,发射器的位填充总是被强制执行。如果需要按照 +位填充规则的要求,零位将被插入,即使它是数据包结束(EOP)信号前的最后一位。接收器必须对NRZI数据进行解码,识别填充位,并将其丢弃。 + +.. caution:: 以下内容可以用一张图概括,了解即可,没有必要死记硬背 + +.. figure:: img/usbstruct.png + +USB 字段(域) +--------------------- + +USB 字段构成了 USB 通信中最基本也是最小的单元,后面的包、事务,最根本都是由字段构成,而字段又是由比特构成。字段部分见手册 8.1。 + +.. note:: USB 的比特先行模式是按照 LSB 先行原则。 + +同步字段 +^^^^^^^^^^^^^^^^^^^^^^^^ + +在 USB 系统中,主机和设备不是共享一个时钟,这使得接收方没办法准确知道发送方什么时候发送数据,尽管能检测到SOP,但是远远不够,所有这个时候就需要同步字段,使得接收方和发送方收发过程中保持同步,所以任何一个包都要以同步字段开始。同步字段0x01,经过编码以后就是01010100B。 + +.. figure:: img/18.png + +包标识符字段 +^^^^^^^^^^^^^^^^^^^^^^^^ + +PID 由一个四位数据包类型字段和一个四位校验字段组成,占用 8 个bit,如图所示。 PID指示数据包的类型,并通过推断,数据包的格式和应用于数据包的错误检测类型包。 PID的四位校验字段是通过执行分组类型字段的一个补码来生成,从而确保PID的可靠解码,以便正确解释分组的其余部分,如果四个PID校验位不是它们各自的分组标识符位的补码,则存在PID错误。 + +.. figure:: img/19.png + +既然是 4个比特,说明了 PID 类型可以分为16种,从16种中,又细分成4类:令牌 PID,数据 PID,握手 PID 和特殊 PID。 + +.. figure:: img/20.png + +地址字段 +^^^^^^^^^^^^^^^^^^^^^^^^ + +地址字段又分为设备地址字段和端点地址字段,其中设备地址字段占用 7 个bit,除去0 地址,主机可以分配的地址有 127个。 + +.. figure:: img/21.png + +端点地址字段占用 4个 bit,总共可以提供 16 个端点。 + +.. figure:: img/22.png + +帧号字段 +^^^^^^^^^^^^^^^^^^^^^^^^ + +帧号字段占用 11 个bit,主机每发出一个帧,帧号都会加1,如图所示。而高速设备中,帧中又包含微帧,1帧=8微帧,微帧则是加0.1。关于帧和微帧的概念,后续补充。 + +.. figure:: img/23.png + +数据字段 +^^^^^^^^^^^^^^^^^^^^^^^^ + +根据传输类型不同,数据字段中的数据长度也是不定的,从 0-1024不等。 + +.. figure:: img/24.png + +CRC 字段 +^^^^^^^^^^^^^^^^^^^^^^^^ + +循环冗余校验(CRC)用于保护令牌和数据包中的所有非PID字段。PID不包含在包含CRC的分组的CRC校验中。 在执行比特填充之前,在发送器中的各个字段上生成所有CRC。 类似地,在去除填充位之后,在接收器中对CRC进行解码。令牌和数据包CRC为所有单比特和双比特错误提供100%的覆盖。 CRC失败被认为表示一个或多个受保护字段已损坏并导致接收器忽略这些字段,并且在大多数情况下,忽略整个数据包。 + +.. figure:: img/24.png + +- 令牌CRC + +为令牌提供五位CRC字段,并覆盖IN,SETUP和OUT令牌的ADDR和ENDP字段或SOF令牌的时间戳字段。 PING和SPLIT特殊令牌还包括一个五位CRC字段。 + +生成多项式为: G(X)= X^5 + X^2 + 1 +表示该多项式的二进制位模式是00101B。 如果接收到所有令牌位而没有错误,则接收器处的五位校验和将为01100B。 + +- 数据CRC + +数据CRC是应用于数据分组的数据字段的16位多项式。 + +生成多项式是:G(X)= X^16 + X^15 + X^2 + 1 +表示该多项式的二进制位模式是1000000000000101B。 如果没有错误地接收到所有数据和CRC位,则16位校验和将为1000000000001101B。 + +USB 包 +--------------------- + +包由字段组成,根据 PID 类型,包分为四大类:令牌包、数据包、握手包、特殊包。此节内容见官方 8.4.1。 + +.. figure:: img/25.png + +算上 SOP,则如图,组成一个完整的包。 + +.. figure:: img/26.png + +令牌包 +^^^^^^^^^^^^^^^^^^^^^^^^ + +令牌包分为:SETUP、IN、OUT、SOF,其中 SETUP、IN、OUT的字段组成一样,如图: + +.. figure:: img/27.png + +- PID 字段:定义了数据传输方向为USB主机到USB设备。 +- ADDR 字段:指明了USB设备地址。 +- ENDP 字段:指明了接收数据的端点号。 +- CRC 字段:用于ADDR字段和ENDP字段进行循环冗余校验。 + +SOF 包的字段组成,如图: + +.. figure:: img/28.png + +- PID 字段:定义了数据传输方向为USB主机到USB设备。 +- 帧号 字段:指明了USB传输的帧号,其11位。 +- CRC 字段:用于ADDR字段和ENDP字段进行循环冗余校验。 + +数据包 +^^^^^^^^^^^^^^^^^^^^^^^^ + +.. figure:: img/29.png + +- PID 字段:用于指明不同的数据包类型。支持 4 种数据包,分别为: DATAO 、 DATA1 、DATA2 和MDATA。 +- 数据 字段:其中包含了传输的数据。其数据的大小根据数据传输类吧和川户需要而定。根据 USB 协议的规定,对于低速 USB 数据传输, 最大长度为8字节对于全速SB 数据传输,其最大长度为 1023 字节;对于高速 USB 数据传输,数据最大长度为 1024 。 +- CRC 字段:这里使用 16 位的循环冗余校验来对数据字段进行保护。 + +握手包 +^^^^^^^^^^^^^^^^^^^^^^^^ + +握手包由8位的PID构成,用于数据传输的末位报告本次数据传输的状成。握手包之后使是整个事务处理的结束信号EOP. + +.. figure:: img/30.png + +特殊包 +^^^^^^^^^^^^^^^^^^^^^^^^ + +USB 事务 +--------------------- + +USB 常用事务共有三种:SETUP、IN、OUT,除了控制传输使用三个事务,其他传输都使用两个事务。特殊事务则是不携带数据的事务。 + +SETUP 事务 +^^^^^^^^^^^^^^^^^^^^^^^^ + +IN 事务 +^^^^^^^^^^^^^^^^^^^^^^^^ + +OUT 事务 +^^^^^^^^^^^^^^^^^^^^^^^^ + +特殊事务 +^^^^^^^^^^^^^^^^^^^^^^^^ + +USB 传输 +--------------------- + +控制传输 +^^^^^^^^^^^^^^^^^^^^^^^^ + +批量传输 +^^^^^^^^^^^^^^^^^^^^^^^^ + +中断传输 +^^^^^^^^^^^^^^^^^^^^^^^^ + +同步传输 +^^^^^^^^^^^^^^^^^^^^^^^^ \ No newline at end of file diff --git a/docs/zh/usb/usb3.0_basic.rst b/docs/zh/usb/usb3.0_basic.rst new file mode 100644 index 00000000..1dbbd815 --- /dev/null +++ b/docs/zh/usb/usb3.0_basic.rst @@ -0,0 +1,33 @@ +USB 基本概念(3.0 为主) +=========================== + + +简介 +------------ + + + +与 USB 2.0 相同和不同点 +-------------------------- + + +Link Layer +-------------------- + +LCW +^^^^^^^^^^ + +Protocol Layer +-------------------- + +LMP +^^^^^^^^^^^^^^^^^^^^^^^^ + +TP +^^^^^^^^^^^^^^^^^^^^^^^^ + +DP +^^^^^^^^^^^^^^^^^^^^^^^^ + +ITP +^^^^^^^^^^^^^^^^^^^^^^^^ \ No newline at end of file diff --git a/docs/zh/usb/usb_desc.rst b/docs/zh/usb/usb_desc.rst new file mode 100644 index 00000000..f0bcc7fe --- /dev/null +++ b/docs/zh/usb/usb_desc.rst @@ -0,0 +1,37 @@ +USB 描述符 +=========================== + +本节参考官方 usb2.0 pdf 9.5 节即可。 + +设备描述符 +--------------------- + +配置描述符 +--------------------- + +接口描述符 +--------------------- + +端点描述符 +--------------------- + +字符串描述符 +--------------------- + +接口关联描述符 +--------------------- + +设备限定描述符 +--------------------- + +其他速度描述符 +--------------------- + +BOS 描述符 +--------------------- + +超高速端点伴随描述符 +--------------------- + +增加型超高速同步端点伴随描述符 +------------------------------- diff --git a/docs/zh/usb/usb_enum.rst b/docs/zh/usb/usb_enum.rst new file mode 100644 index 00000000..1434424f --- /dev/null +++ b/docs/zh/usb/usb_enum.rst @@ -0,0 +1,22 @@ +USB 枚举 +=========================== + +当我们了解了 usb 设备请求以后,就可以来学习下 USB 设备的整个枚举过程了,看看是如何枚举出一个串口、鼠标、u盘等设备了。枚举过程中主机会发送设备请求来获取相关信息(也就是描述符),具体发送哪些,参考下图。 + +.. figure:: img/usb_enum.png + +- 首先设备接上 USB 线,然后插上电脑 +- 设备插上以后上电,处于供电状态 +- 主机通过 D+/D- 识别到设备插入 +- 对设备进行复位 +- 主机发送 **获取设备描述符请求** +- 可选的复位操作 +- 主机发送 **设置设备地址请求** +- 主机发送 **获取配置描述符请求**,可能会获取多次,无所谓 +- 主机发送 **获取字符串描述符请求**,正常会获取3个字符串,如果后面的描述符中指定了字符串,则继续获取指定的字符串 +- 主机发送 **获取设备限定描述符请求**,用来获取在设备工作在其他速度上的请求,如果设备只能工作在全速模式,则必须回复 stall,并且协议栈中一定会打印该请求告诉你此命令设备不支持。 +- 主机发送 **设置配置请求**,对设备的端点进行配置,通常是根据端点描述符中的配置进行设置。 +- 到此标准的设备请求结束 +- 主机根据接口描述符加载对应支持的 class 驱动,如果主机不支持,则会提示该设备找不到驱动 +- 加载完成以后,开始执行该 class 相关的请求 +- 最终进行 class 的数据流传输 \ No newline at end of file diff --git a/docs/zh/usb/usb_ext.rst b/docs/zh/usb/usb_ext.rst new file mode 100644 index 00000000..86b87a53 --- /dev/null +++ b/docs/zh/usb/usb_ext.rst @@ -0,0 +1,39 @@ +.. _usb_ext: + +USB 知识点拓展 +=========================== + +什么是分包 +------------- + +由于 USB 协议中规定了每个包的最大长度,所以当我们发送的数据长度超过了最大包长度时,就需要分包发送,这就是分包。比如 ep mps 为 64,数据长度为 129,则 USB 会按照 64 + 64 + 1 的形式传输。 +而对于 USB IP 来说,分包分为软件分包和硬件分包,软件分包就是用户代码自行分包,这种 ip 一般都使用 FIFO 来进行,因为 FIFO 深度是有限的;第二种 +则是使用硬件分包,这种 USB IP 一般带 DMA 或者描述符 DMA 功能,那么这种 IP 的效率无疑是最高的,cherryusb 中充分利用了这点,使得 USB 速度能够达到最高。 + +对于软件分包来说,一次发送的长度即使是 16K, **内部也是通过软件分包的,在这种情况下,发送长度的多少不会对速度有任何提升**。 +对于硬件分包来说,发送的长度会影响速度,因为硬件分包是通过 DMA 来进行的, **一次发送的长度越大,DMA 的效率就越高,速度也就越快**。(当然,其他协议栈虽然使用了 dma,但是部分代码实现还是按照一个包进行,等于没用,这也是速度低的一个原因) + +什么是短包 +---------------- + +在上面我们讲了分包之后,短包就是分包的最后一个包(并且长度小于 EP MPS).比如发送 129 字节的数据,那么 USB 会按照 64 + 64 + 1 的形式传输,最后一个包是1个字节,这1个字节就是短包。 + +什么是 ZLP +------------- + +ZLP,顾名思义,零长度数据包,也就是数据长度为0 的短包。是 USB 设备在数据传输结束时,如果数据长度正好是最大包长度的整数倍,那么就需要发送一个 ZLP 数据包,用来告诉对方数据传输结束。 + +.. caution:: ZLP 功能仅限于 CONTROL 和 BULK 传输 + +什么时候算中断完成 +-------------------- + +从机接收:接收的长度与设置的长度相等;接收的最后一个包为短包。 +从机发送:发送的长度与设置的长度相等,如果发送的长度是 EP MPS 的整数倍, **通常** 需要再发送一个 ZLP(仅限 control 和 bulk 传输)。 + +.. note:: 对于从机接收,并且是 bulk 传输,接收长度通常设计为 EP MPS,以下三种情况可以修改为多个 EP MPS: 固定长度;自定义协议并携带长度(例如 MSC); 主机手动发送 ZLP 或者短包(例如 RNDIS) + +.. note:: 对于从机发送,并且是 bulk 传输,发送长度没有限制,但是如果是 EP MPS 整数倍,通常需要发送 ZLP。自定义协议则不需要发送 ZLP,例如 MSC。 + +主机接收:同从机接收 +主机发送:发送的长度与设置的长度相等 diff --git a/docs/zh/usb/usb_request.rst b/docs/zh/usb/usb_request.rst new file mode 100644 index 00000000..8e42565d --- /dev/null +++ b/docs/zh/usb/usb_request.rst @@ -0,0 +1,6 @@ +USB 设备请求 +=========================== + +本节参考官方 usb2.0 pdf 9.3、9.4 节即可。 + +.. figure:: img/usb_request.png diff --git a/docs/zh/usbdev.svg b/docs/zh/usbdev.svg new file mode 100644 index 00000000..8f787289 --- /dev/null +++ b/docs/zh/usbdev.svg @@ -0,0 +1,4 @@ + + + +
usbd_desc_register
usbd_add_interface
usbd_add_endpoint
    struct usbd_tx_rx_msg tx_msg[16];
    struct usbd_tx_rx_msg rx_msg[16];
struct usbd_interface *intf[16];
usbd_initialize
USBD_IRQHandler
usbd_event_reset_handler
usbd_event_ep0_setup_complete_handler
usbd_event_ep_in_complete_handler
usbd_event_ep_out_complete_handler
usbd_setup_request_handler
tx_msg[ep & 0x7f].cb
rx_msg[ep & 0x7f].cb
usbd_event_ep0_in_complete_handler
tx_msg[ep & 0x7f].cb (ep != 0)
usbd_event_ep0_out_complete_handler
rx_msg[ep & 0x7f].cb (ep != 0)
usbd_standard_request_handler
usbd_class_request_handler
usbd_vendor_request_handler
\ No newline at end of file diff --git a/docs/zh/usbhost.svg b/docs/zh/usbhost.svg new file mode 100644 index 00000000..b7d537b5 --- /dev/null +++ b/docs/zh/usbhost.svg @@ -0,0 +1,9 @@ +
usbh_initialize
usbh_initialize
usbh_hub_initialize
usbh_hub_initialize
usbh_roothub_register
usbh_roothub_register
create usbh_hub_thread
create usbh_hub_thread
usb_hc_init
usb_hc_init
usbh_roothub_thread_wakeup
usbh_roothub_thread_wakeup +
hub_int_complete_callback
hub_int_complete_callback +
wakeup
wakeup
wakeup
wakeup
usbh_enumerate
usbh_enumerate +
search all ports
search all ports
usbh_hub_events
usbh_hub_events +
CLASS_CONNECT
CLASS_CONNECT +
search all interface drivers
search all interface drivers
usbh_find_class_driver
usbh_find_class_driver +
if hub class?
if hub class?
usbh_int_urb_fill


usbh_submit_urb
usbh_int_urb_fill...
Class Register
Class Register +
USBH_IRQHandler
USBH_IRQHandler +
Viewer does not support full SVG 1.1
\ No newline at end of file diff --git a/docs/zh/usbip/cdns2.rst b/docs/zh/usbip/cdns2.rst new file mode 100644 index 00000000..88afc8d2 --- /dev/null +++ b/docs/zh/usbip/cdns2.rst @@ -0,0 +1,2 @@ +CDNS2 +=============== diff --git a/docs/zh/usbip/cdns3.rst b/docs/zh/usbip/cdns3.rst new file mode 100644 index 00000000..c2132d1a --- /dev/null +++ b/docs/zh/usbip/cdns3.rst @@ -0,0 +1,2 @@ +CDNS3 +=============== diff --git a/docs/zh/usbip/chipidea.rst b/docs/zh/usbip/chipidea.rst new file mode 100644 index 00000000..57c46ec0 --- /dev/null +++ b/docs/zh/usbip/chipidea.rst @@ -0,0 +1,2 @@ +CHIPIDEA +================= \ No newline at end of file diff --git a/docs/zh/usbip/dwc2.rst b/docs/zh/usbip/dwc2.rst new file mode 100644 index 00000000..6c5a8c08 --- /dev/null +++ b/docs/zh/usbip/dwc2.rst @@ -0,0 +1,2 @@ +DWC2 +================= \ No newline at end of file diff --git a/docs/zh/usbip/dwc3.rst b/docs/zh/usbip/dwc3.rst new file mode 100644 index 00000000..746bbee6 --- /dev/null +++ b/docs/zh/usbip/dwc3.rst @@ -0,0 +1,2 @@ +DWC3 +=============== diff --git a/docs/zh/usbip/ehci.rst b/docs/zh/usbip/ehci.rst new file mode 100644 index 00000000..637bbe69 --- /dev/null +++ b/docs/zh/usbip/ehci.rst @@ -0,0 +1,2 @@ +EHCI +================= \ No newline at end of file diff --git a/docs/zh/usbip/fotg210.rst b/docs/zh/usbip/fotg210.rst new file mode 100644 index 00000000..f6e566a8 --- /dev/null +++ b/docs/zh/usbip/fotg210.rst @@ -0,0 +1,2 @@ +FOTG210 +=============== diff --git a/docs/zh/usbip/musb.rst b/docs/zh/usbip/musb.rst new file mode 100644 index 00000000..597876c0 --- /dev/null +++ b/docs/zh/usbip/musb.rst @@ -0,0 +1,2 @@ +MUSB +================= \ No newline at end of file diff --git a/docs/zh/usbip/ohci.rst b/docs/zh/usbip/ohci.rst new file mode 100644 index 00000000..8467233b --- /dev/null +++ b/docs/zh/usbip/ohci.rst @@ -0,0 +1,2 @@ +OHCI +================= \ No newline at end of file diff --git a/docs/zh/usbip/xhci.rst b/docs/zh/usbip/xhci.rst new file mode 100644 index 00000000..0c16c2e2 --- /dev/null +++ b/docs/zh/usbip/xhci.rst @@ -0,0 +1,2 @@ +XHCI +================= \ No newline at end of file diff --git a/docs/zh/version.rst b/docs/zh/version.rst new file mode 100644 index 00000000..5c6e23e7 --- /dev/null +++ b/docs/zh/version.rst @@ -0,0 +1,182 @@ +版本说明 +============================== + +如果没有特别情况,请使用最新版本。下面只列举比较重要的更新,详细更新说明请参考 https://github.com/cherry-embedded/CherryUSB/releases。 + +<= v0.10.2 初代版本 +---------------------- + +- **用于定基本的主从机框架,仅支持单 USB IP**。 +- **host 驱动每个 ep 占用一个 硬件 pipe,不支持动态使用硬件 pipe**。 +- 相关 porting 需要使用此版本,后续不再支持(比如 ch32,rp2040),以及旧版本pusb2 和 xhci(新版本不再提供源码)。 + +v1.0.0 过度版本 +---------------------- + +- **host 支持动态使用硬件 pipe,不再固定** + +v1.1.0 过度版本 +---------------------- + +- **主从机支持多 USB IP 且要相同 IP** +- **host 增加 bluetooth, ch340, ftdi, cp210x, asix 驱动** +- device msc 支持多 lun,并且 CONFIG_USBDEV_MSC_BLOCK_SIZE 修改为 CONFIG_USBDEV_MSC_MAX_BUFSIZE + +v1.2.0 +---------------------- + +- **host 增加 rtl8152,cdc ncm 驱动** +- host 增加 timer 去控制中断传输(hub修改为 timer 控制) +- porting 增加 esp,aic 主机驱动 +- **优化 DWC2 优化代码方便阅读,并增加一些 FIFO 配置宏给用户(因为 dwc2 fifo 大小有限,以及配置方式很多,所以导出给用户配置,方便合理控制性能)** +- 优化 ehci 驱动(qtd不再使用动态申请,绑定 qh),方便代码运行的更快 + +v1.3.0 +---------------------- + +- **device 支持多种速度描述符自动选择功能(开启 CONFIG_USBDEV_ADVANCE_DESC)** +- device core 代码统一 ep0 buffer 的使用,用于美化代码 +- host 增加 pl2303 驱动;采用 id table 来支持多个 vid,pid;增加 user_data 给用户使用 +- host 网络 class 驱动增加 tx、rx buffer 的宏,增加 LWIP_TCPIP_CORE_LOCKING_INPUT 的使用,以便实现数据的零拷贝 +- porting 导入 bouffalo,aic,stm32f723 device驱动 +- **porting 中主机部分 urb->timeout 清0 的处理有点问题(大数据量传输时会出现 no pipe alloc 异常,主要原因是刚启动传输就完成了,还没判断 timeout就被修改为0了,没有进入 take sem 流程),此版本已修复** +- ehci enable iaad in usbh_kill_urb,read ehci hcor offset from hccr caplength,enable ohci for ehci +- 适配 nuttx os + +v1.3.1 +---------------------- + +- bugfix(audio,video,cdc ecm 相关宏,结构体,api) +- **host hub 枚举线程删除,使用 psc 线程,枚举方式更改为队列模式,取消同时枚举多个设备的功能** +- host 扫描驱动信息和 instance 采用递归模式,删除链表扫描 +- host 网络 class 驱动优化,支持接收 16K 以上的数据(cdc ecm 不支持),采用高级 memcpy api +- **device 协议栈中打印删除(中断中不再做打印)** +- porting 中 musb fifo配置修改为从 fifo table 获取(此代码参考 linux),适配 es32,sunxi,beken + +v1.4.0 +---------------------- + +- **device 开始支持 remote wakeup 功能, hid request(0x21),完善 GET STATUS 请求(此版本开始可以通过 USB3CV 测试)** +- device 增加 UF2, ADB, WEBUSB 功能; msc 增加裸机的读写 polling 功能,将读写放在 while1中执行; usbd_cdc 改名为 usbd_cdc_acm +- host 增加 usbwifi(bl616), xbox驱动; **重构 USB3.0 枚举逻辑** +- **host 中 cdc_acm,hid,msc,serial 传输共享 buffer,如果存在多个相同的设备会有问题,修改为单独的 buffer** +- **porting 重构 XHCI/PUSB2 驱动,不开源**;ehci 和 ohci 文件改名;增加 remote wakeup api +- esp 组件库支持 +- **chipidea 从机驱动支持,nxp mcx 系列主从支持** +- threadx os 支持 + +v1.4.1 +---------------------- + +- **修复device 模式下使用多个 altsetting 时重复关闭端点问题,改成 altsetting 为0时关闭** +- **重构主机 audio 解析描述符** +- **增加 kinetis usbip** +- 主机下 usbh_msc_get_maxlun 请求部分 U 盘不支持,不做错误返回 +- 主机下 usbh_hid_get_report_descriptor 导出给用户调用 +- 静态代码检查 +- github action 功能 + +v1.4.2 +---------------------- + +- device 实现 USB_REQUEST_GET_INTERFACE 请求 +- **device video 传输重构,增加双缓冲功能** +- device ecm 重构,保持和 rndis 类似 API +- device 和 host audio 音量配置功能重构 +- host 增加 AOA 驱动 +- 兼容 C++ 相关修改 +- fsdev 不支持 ISO 和 DWC2 高速 hub 不支持全速低速检查 +- **通用 OHCI 代码更新** + +v1.4.3 +---------------------- + +- **device ep0 处理增加线程模式** +- device audio feedback 宏和demo +- device rndis 增加透传功能(无LWIP) +- **host msc 将 scsi 初始化从枚举线程中移出,在mount阶段调用,并增加了testunity 多次尝试,兼容一部分 U 盘** +- rp2040 主从支持 +- **nuttx fs,serial,net 组件支持** +- dwc2、ehci、ohci 主机 dcache功能支持(v1.5.0 完善) +- t113、MCXA156、CH585 、 **stm32h7r 支持** +- 修复 v1.4.1 中 altsetting 为0时应该关闭所有端点的问题 + +v1.5.0 +---------------------- + +- **协议栈内部全局 buffer 需要使用 USB_ALIGN_UP 对齐, 用于开启 dcache 并且不使能 nocache 时使用** +- **完善 ehci/ohci dcache 模式下的处理**, add CONFIG_USB_EHCI_DESC_DCACHE_ENABLE for qh&qtd&itd, add CONFIG_USB_OHCI_DESC_DCACHE_ENABLE for ed&td +- **平台代码更新,平台相关转移到 platform,增加 lvgl 键鼠支持,blackmagic 支持,filex 支持, zephyr disk支持,esp-idf netif支持** +- **device sof callback 支持** +- **dwc2 、fsdev st 下实现底层 API 和中断,直接调用 HAL_PCD_MSP 和 HAL_HCD_MSP,不需要用户复制粘贴** +- **DWC2 实现 SPLIT 功能,高速模式下支持外部高速 hub 对接 FS/LS 设备** +- liteos-m, zephyr os 支持 +- device msc 裸机读写采用变量模式,而不是ringbuffer +- ehci qtd 使用 qtd alloc & free,节省内存,目前是 qh 携带 qtd +- rndis/ECM device, msc demo 更新,支持 rt-thread 下免修改 +- **memcpy 全部使用 usb_memcpy 替换,arm 库存在非对其访问问题** +- **重构 device mtp 驱动(收费使用)** +- **device tmc 驱动(收费使用)** +- **重构device video 传输,直接在图像数据中填充 uvc header,达到zero memcpy** +- **增加 usb_osal_thread_schedule_other api,用于在释放 class 资源之前,先释放所有 class 线程,避免释放 class 资源以后线程还在使用该 class 资源** +- **dwc2 device 增加 dcache 功能,可用于 cortex-M7/ESP32P4** +- **bouffalo/hpm/esp/st/nxp dcache api 支持** +- ch32 device iso 更新,IP 目录重新分类 +- cmake,scons,kconfig 更新 +- 使用 USB_ASSERT_MSG 对部分代码检查,全面性 warning 修复 +- N32H4/MM32F5 device 支持 +- 默认使能 CONFIG_USBDEV_ADVANCE_DESC + +v1.5.1 +---------------------- + +- 支持 rt-thread 下使用 adb shell,host serial/device cdc_acm 对接 rtdevice 框架 +- **dwc2 增加多个 usbport 不同参数的配置功能,比如一个全速一个高速,fifo配置和phy配置不同** +- **ehci 在控制传输中如果没有 nodata 阶段会导致 data qtd 未释放,导致内存泄漏** +- **dwc2 读取 setup 使用 usbd_get_next_ep0_state 去判断,避免 setup 和 ep0 out 使用在 USB_OTG_DOEPINT_XFRC 状态下冲突** +- sifli usb device 初步支持 + +v1.5.2 +---------------------- + +- 对 1.5.1 下 rt-thread 组件的一些 bugfix +- idf timer osal 替换为 esp timer,freertos timer会有启动失败的可能性;xTaskCreate 使用 xTaskCreatePinnedToCore 替换,方便多核使用 +- 主机枚举中,删除描述符溢出相关的 ASSERT 操作,改成返回错误。获取字符串描述符改成支持才获取。2 ms 延时改成 10ms,因为一些 os 使用的是 100hz,会造成延时失效 +- **dwc2 ep mult 支持,split 传输代码优化,对 split 相关的 cache 处理修改** +- **dwc2 halt 中不能清除 USB_OTG_HCCHAR_EPDIR,reset port 中使用超时机制,防止在枚举时由于拔出而造成死等** +- 更新 DWC2 中 at32,stm32,kendryte,espressif glue 代码 +- musb 对于标准的 IP 结构采用独立 EP 控制寄存器组,不使用 EPIDX 寄存器去控制 +- 删除所有 CONFIG_USBDEV_EP_NUM & CONFIG_USBHOST_PIPE_NUM,不再使用,因为 IP 本身会携带这些信息,或者厂家 SDK 提供了对应的宏 +- CONFIG_USBHOST_MAX_INTF_ALTSETTINGS 默认使用 2 减少内存,只有 UVC 和UAC 使用(商业收费),所以不需要开很大 +- urb interval 从 u8 改 u32,最大支持 2^15 * 125us + +v1.5.3 +---------------------- + +- 增加 mongoose demo +- **从机支持自定义 ep0 mps,仅支持商业性 IP** +- 主机增加 UVC bulk支持, **接口号匹配驱动功能**, **主机分配地址功能改成循环自增模式** ,重构 lsusb 命令 +- 主机控制传输增加 retry 机制,部分 device 通信不稳定,retry 次数参考 linux +- **主机 rndis 驱动增加非标 02/02/ff 接口驱动匹配** +- musb IP 关闭 multipoint feature 支持 +- hpmicro、chipidea dcache 支持 +- idf host msc 支持 +- otg 框架重构,当前 port 仅支持 hpmicro +- CI 编译功能,支持 hpmicro/espressif/bouffalolab + +v1.5.3.99 +---------------------- + +bugfix for v1.5.3 + + +v1.6.0 +---------------------- + +- **host 增加 serial 框架,统一所有类串口驱动** +- **host hid 增加报告描述符解析功能** +- usbh_initialize 增加 event callback,用于通知用户主机事件变化,通常不需要使用,设置为 NULL 即可 +- 支持 gamepad device +- 增加 ti xmc,infineon edge e8x port 支持 +- dwc2 增加 usbd_dwc2_get_system_clock 替换 SystemCoreClock;删除 __UNALIGNED_UINT32_READ 和 __UNALIGNED_UINT32_WRITE 宏;读取 setup 个数设置为 1个;第一次读取 setup 移动到 USB_OTG_GINTSTS_ENUMDNE 中断中 +- dwc2/ehci 增加 roothub 速度设置 \ No newline at end of file diff --git a/idf_component.yml b/idf_component.yml index 9642e0e2..bcae2d65 100644 --- a/idf_component.yml +++ b/idf_component.yml @@ -1,4 +1,4 @@ -version: "1.5.3" +version: "1.6.0" description: CherryUSB is a tiny and portable USB Stack (device & host) for embedded system with USB IP tags: - usb -- cgit v1.3.1