3

TinyUSB 基本使用

 3 years ago
source link: https://www.taterli.com/7812/
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

TinyUSB 基本使用

  • TaterLi
  • 2021年5月6日2021年5月6日

由于早期时候我们产品基于STM32开发,自然而然的用了STM32的USB库,这个本身没什么问题,库也很完善,而且有官方在完善,这本来是个不错的东西,但是随着ST的缺货,问题就越来越多,比如别人的芯片可不会兼容ST的库,如果是标准设备那还好,如果像我们还做HOTP Key这样的,移植起来就相当的麻烦.一开始他们推荐我使用RL-USB,但是RL-USB始终是挂载RTX上的,至于哪一天RTX也出毛病,这就太惨了,为了避免被各种平台捆绑,我选择了TinyUSB,这个库目前对Host模式支持还不是很好,但是Deivce模式基本上没毛病,如果要兼容适配其他平台,只需要适配一些函数即可,当然Host模式暂时还不完善,先用STM32来测试.

移植好的工程从这里下载:https://github.com/nickfox-taterli/tinyusb_stm32f769disco (请不要在线下载ZIP,因为这样并不完整.)

移植只需要几步,第一步添加用到的文件,如下:

  • 属于工程专用文件:usb_descriptors.c tusb_config.h usb_descriptors.h
  • 属于库内文件:tusb.c *_device.c tusb_fifo.c dcd_*.c usbd.c usbd_control.c

只有属于工程专属文件,才是我们需要开发的,我这里是从hid_composite例子中挪过来的,然后修改tusb_config.h文件来指定设备属性.查看完整文件:https://github.com/nickfox-taterli/tinyusb_stm32f769disco/blob/main/Core/Inc/tusb_config.h#L37

#define CFG_TUSB_MCU OPT_MCU_STM32F7
#define BOARD_DEVICE_RHPORT_NUM 1
#define BOARD_DEVICE_RHPORT_SPEED OPT_MODE_HIGH_SPEED

之后还要给出端口的配置,这个根据实际PCB来修改,这里修改的是main.c,具体文件:https://github.com/nickfox-taterli/tinyusb_stm32f769disco/blob/main/Core/Src/main.c#L105

void board_init(void)
{
  LL_GPIO_InitTypeDef GPIO_InitStruct;
  // Enable All GPIOs clocks
  LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_GPIOA);
  LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_GPIOB);
  LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_GPIOC);
  LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_GPIOD);
  LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_GPIOG);
  LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_GPIOH);
  LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_GPIOI);
  LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_GPIOJ);

  /* ULPI CLK */
  GPIO_InitStruct.Pin = LL_GPIO_PIN_5;
  GPIO_InitStruct.Mode = LL_GPIO_MODE_ALTERNATE;
  GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_VERY_HIGH;
  GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
  GPIO_InitStruct.Pull = LL_GPIO_PULL_NO;
  GPIO_InitStruct.Alternate = LL_GPIO_AF_10;
  LL_GPIO_Init(GPIOA, &GPIO_InitStruct);

  /* ULPI D0 */
  GPIO_InitStruct.Pin = LL_GPIO_PIN_3;
  GPIO_InitStruct.Mode = LL_GPIO_MODE_ALTERNATE;
  GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_VERY_HIGH;
  GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
  GPIO_InitStruct.Pull = LL_GPIO_PULL_NO;
  GPIO_InitStruct.Alternate = LL_GPIO_AF_10;
  LL_GPIO_Init(GPIOA, &GPIO_InitStruct);

  /* ULPI D1 D2 D3 D4 D5 D6 D7 */
  GPIO_InitStruct.Pin = LL_GPIO_PIN_0 | LL_GPIO_PIN_1 | LL_GPIO_PIN_10 | LL_GPIO_PIN_11 | LL_GPIO_PIN_12 | LL_GPIO_PIN_13 | LL_GPIO_PIN_5;
  GPIO_InitStruct.Mode = LL_GPIO_MODE_ALTERNATE;
  GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_VERY_HIGH;
  GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
  GPIO_InitStruct.Pull = LL_GPIO_PULL_NO;
  LL_GPIO_Init(GPIOB, &GPIO_InitStruct);

  /* ULPI STP */
  GPIO_InitStruct.Pin = LL_GPIO_PIN_0 | LL_GPIO_PIN_2;
  GPIO_InitStruct.Mode = LL_GPIO_MODE_ALTERNATE;
  GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_VERY_HIGH;
  GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
  GPIO_InitStruct.Pull = LL_GPIO_PULL_NO;
  LL_GPIO_Init(GPIOC, &GPIO_InitStruct);

  /* NXT */
  GPIO_InitStruct.Pin = LL_GPIO_PIN_4;
  GPIO_InitStruct.Mode = LL_GPIO_MODE_ALTERNATE;
  GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_VERY_HIGH;
  GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
  GPIO_InitStruct.Pull = LL_GPIO_PULL_NO;
  LL_GPIO_Init(GPIOH, &GPIO_InitStruct);

  /* ULPI DIR */
  GPIO_InitStruct.Pin = LL_GPIO_PIN_11;
  GPIO_InitStruct.Mode = LL_GPIO_MODE_ALTERNATE;
  GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_VERY_HIGH;
  GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
  GPIO_InitStruct.Pull = LL_GPIO_PULL_NO;
  LL_GPIO_Init(GPIOI, &GPIO_InitStruct);

  // Enable USB HS & ULPI Clocks
  LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_OTGHSULPI);
  LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_OTGHS);

  // No VBUS sense
  USB_OTG_HS->GCCFG &= ~USB_OTG_GCCFG_VBDEN;

  // B-peripheral session valid override enable
  USB_OTG_HS->GOTGCTL |= USB_OTG_GOTGCTL_BVALOEN;
  USB_OTG_HS->GOTGCTL |= USB_OTG_GOTGCTL_BVALOVAL;

  // Force device mode
  USB_OTG_HS->GUSBCFG &= ~USB_OTG_GUSBCFG_FHMOD;
  USB_OTG_HS->GUSBCFG |= USB_OTG_GUSBCFG_FDMOD;
}

现在USB就正常工作了~


如何移植,这个问题就相当的复杂了,我们需要分离仓库,针对每个平台分离单独的仓库,然后对齐进行推送,具体移植内容在这里 => https://github.com/hathach/tinyusb/tree/master/src/portable,如果你的芯片不是大家所熟知的,那么大概率过不了PR,你需要非常熟悉USB的工作流,这样才能很好的移植.由于这个不具备通用性,我就不再展开讨论了.(或者后续会写)

发表评论 取消回复

您的电子邮箱地址不会被公开。 必填项已用*标注

评论

显示名称 *

电子邮箱地址 *

网站网址


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK