From 3c0130ba4f3d1897062fa159797f3376a369e7a2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?King=20K=C3=A9vin?= Date: Fri, 3 Jan 2020 19:39:41 +0100 Subject: [PATCH] USB: unify and improve USB (dis)connect --- lib/usb_cdcacm.c | 18 +++++++++--------- lib/usb_dfu.c | 20 +++++++++++--------- 2 files changed, 20 insertions(+), 18 deletions(-) diff --git a/lib/usb_cdcacm.c b/lib/usb_cdcacm.c index 659874e..4cdcf6e 100644 --- a/lib/usb_cdcacm.c +++ b/lib/usb_cdcacm.c @@ -247,7 +247,7 @@ static const char* usb_strings[] = { "DFU bootloader (runtime mode)", /**< DFU interface string */ }; -/** disconnect USB by pulling down D+ to for re-enumerate */ +/** disconnect USB to force re-enumerate */ static void usb_disconnect(void) { if (usb_device) { @@ -258,18 +258,12 @@ static void usb_disconnect(void) rcc_periph_clock_enable(RCC_GPIOB); gpio_set_mode(GPIOB, GPIO_MODE_OUTPUT_2_MHZ, GPIO_CNF_OUTPUT_PUSHPULL, GPIO9); gpio_set(GPIOB, GPIO9); - for (uint32_t i = 0; i < 0x2000; i++) { // wait for at least 10 ms - __asm__("nop"); - } -#else +#endif // pull USB D+ low for a short while rcc_periph_clock_enable(RCC_GPIOA); gpio_set_mode(GPIOA, GPIO_MODE_OUTPUT_2_MHZ, GPIO_CNF_OUTPUT_PUSHPULL, GPIO12); gpio_clear(GPIOA, GPIO12); - for (uint32_t i = 0; i < 0x2000; i++) { // wait for at least 10 ms - __asm__("nop"); - } -#endif + sleep_ms(50); // USB disconnected must be at least 10 ms long, at most 100 ms } /** DFU detach (disconnect USB and perform core reset) @@ -447,6 +441,12 @@ void usb_cdcacm_setup(void) // initialize USB rcc_periph_reset_pulse(RST_USB); // reset USB peripheral usb_disconnect(); // disconnect to force re-enumeration +#if defined(MAPLE_MINI) + // connect USB D+ using dedicated DISC line/circuit on PB9 + rcc_periph_clock_enable(RCC_GPIOB); + gpio_set_mode(GPIOB, GPIO_MODE_OUTPUT_2_MHZ, GPIO_CNF_OUTPUT_PUSHPULL, GPIO9); + gpio_clear(GPIOB, GPIO9); +#endif rcc_periph_clock_enable(RCC_GPIOA); // enable clock for GPIO used for USB rcc_periph_clock_enable(RCC_USB); // enable clock for USB domain usb_device = usbd_init(&st_usbfs_v1_usb_driver, &usb_cdcacm_device_descriptor, &usb_cdcacm_configuration_descriptor, usb_strings, LENGTH(usb_strings), usbd_control_buffer, sizeof(usbd_control_buffer)); diff --git a/lib/usb_dfu.c b/lib/usb_dfu.c index c8ea755..eac8b31 100644 --- a/lib/usb_dfu.c +++ b/lib/usb_dfu.c @@ -131,24 +131,20 @@ static const char *usb_dfu_strings[] = { /** disconnect USB to force re-enumerate */ static void usb_disconnect(void) { + if (usb_device) { + usbd_disconnect(usb_device, true); + } #if defined(MAPLE_MINI) // disconnect USB D+ using dedicated DISC line/circuit on PB9 rcc_periph_clock_enable(RCC_GPIOB); gpio_set_mode(GPIOB, GPIO_MODE_OUTPUT_2_MHZ, GPIO_CNF_OUTPUT_PUSHPULL, GPIO9); gpio_set(GPIOB, GPIO9); - for (uint32_t i = 0; i < 0x2000; i++) { - __asm__("nop"); - } - gpio_clear(GPIOB, GPIO9); -#else +#endif // pull USB D+ low for a short while rcc_periph_clock_enable(RCC_GPIOA); gpio_set_mode(GPIOA, GPIO_MODE_OUTPUT_2_MHZ, GPIO_CNF_OUTPUT_PUSHPULL, GPIO12); gpio_clear(GPIOA, GPIO12); - for (uint32_t i = 0; i < 0x2000; i++) { - __asm__("nop"); - } -#endif + sleep_ms(50); // USB disconnected must be at least 10 ms long, at most 100 ms } /** flash downloaded data block @@ -311,6 +307,12 @@ void usb_dfu_setup(void) rcc_periph_reset_pulse(RST_USB); // reset USB peripheral usb_disconnect(); // disconnect to force re-enumeration +#if defined(MAPLE_MINI) + // connect USB D+ using dedicated DISC line/circuit on PB9 + rcc_periph_clock_enable(RCC_GPIOB); + gpio_set_mode(GPIOB, GPIO_MODE_OUTPUT_2_MHZ, GPIO_CNF_OUTPUT_PUSHPULL, GPIO9); + gpio_clear(GPIOB, GPIO9); +#endif rcc_periph_clock_enable(RCC_GPIOA); // enable clock for GPIO used for USB rcc_periph_clock_enable(RCC_USB); // enable clock for USB domain usb_device = usbd_init(&st_usbfs_v1_usb_driver, &usb_dfu_device, &usb_dfu_configuration, usb_dfu_strings, LENGTH(usb_dfu_strings), usbd_control_buffer, sizeof(usbd_control_buffer)); // configure USB device