diff --git a/src/platforms/swlink/Makefile.inc b/src/platforms/swlink/Makefile.inc index aeee95a..0287d1d 100644 --- a/src/platforms/swlink/Makefile.inc +++ b/src/platforms/swlink/Makefile.inc @@ -26,6 +26,7 @@ SRC += cdcacm.c \ serialno.c \ timing.c \ timing_stm32.c \ + platform_common.c \ all: blackmagic.bin blackmagic_dfu.bin blackmagic_dfu.hex diff --git a/src/platforms/swlink/Readme b/src/platforms/swlink/Readme index b4b3c2c..b6a442e 100644 --- a/src/platforms/swlink/Readme +++ b/src/platforms/swlink/Readme @@ -1,10 +1,30 @@ -Blackmagic for the STM8S Discovery Board -======================================== +Blackmagic for STM8S Discovery and STM32F103 Minimum System Development Board +============================================================================= + +* External connections: + +Function PIN STM8S-DISCO BLUPILL +JTMS/SWDIO PA13 CN5/5 P2/2 +TTCK/SWCLK PA14 CN5/4 P2/3 +JTDI PA15 CN5/6 P4/11 (38) +JTDO PB3 CN5/3 P4/10 (39) +SRST PB4 CN5/8 P4/9 (40) + +UART1_TX PB6 CN7/4 P4/7 (42) +UART1_RX PB7 CN7/2 P4/6 (43) + +References: +https://www.st.com/resource/en/user_manual/cd00250600.pdf +Blue Pill: +https://jeelabs.org/img/2016/STM32F103C8T6-DEV-BOARD-SCH.pdf (first number) +https://wiki.stm32duino.com/images/a/ae/Bluepillpinout.gif (second number) + +* STM8S Discovery The board is a ST-Link V1 Board, but with access to JTAG pins accessible on CN5. This allows easy reprogramming and reuse of the JTAG header. Programmatical it seems indistinguishable from a e.g. STM32VL -Discovery. So here avariant that uses CN5 for JTAG/SWD_TRACESWO and CN7 for +Discovery. So here a variant that uses CN5 for JTAG/SWD and CN7 for UART. Force Bootloader entry is done with shorting CN7 Pin3/4 so PB6 read low while @@ -13,3 +33,17 @@ pulled up momentary by PB6. Reuse SWIM Pins for Uart (USART1) RX: CN7 Pin2 ->SWIM_IN (PB7)/USART1_RX / SWIM_IN(PB9) TX: CN7 Pin4 -> SWIM_RST_IN(PB6)/USART1_TX + +* STM32F103 Minimum System Development Board (aka Blue Pill) + +This board has the SWD pins of the onboard F103 accessible on one side. +Reuse these pins. There are also jumpers for BOOT0 and BOOT1(PB2). Reuse +Boot1 as "Force Bootloader entry" jumpered high when connecting to USB. Boot1 +has 100 k Ohm between MCU and header pin and can not be used as SRST. + +All other port pins are have header access with headers not yet soldered. +JTAG TDO: PB3 +JTAG TDI: PA15 +SWD SWO: PA10 (use Uart pin as on normal STLINK) + +Distinguish boards by checking the SWIM_IN connection PB9/PB10 diff --git a/src/platforms/swlink/platform.c b/src/platforms/swlink/platform.c index 9115085..3aa5477 100644 --- a/src/platforms/swlink/platform.c +++ b/src/platforms/swlink/platform.c @@ -18,8 +18,9 @@ * along with this program. If not, see . */ -/* This file implements the platform specific functions for the ST-Link - * implementation. +/* This file implements the platform specific functions for ST-Link + * on the STM8S discovery and STM32F103 Minimum System Development Board, also + * known as bluepill. */ #include "general.h" @@ -34,6 +35,13 @@ #include #include +static uint8_t rev; + +int platform_hwversion(void) +{ + return rev; +} + void platform_init(void) { uint32_t data; @@ -44,10 +52,8 @@ void platform_init(void) #endif rcc_clock_setup_in_hse_8mhz_out_72mhz(); + rev = detect_rev(); /* Enable peripherals */ - rcc_periph_clock_enable(RCC_USB); - rcc_periph_clock_enable(RCC_GPIOA); - rcc_periph_clock_enable(RCC_GPIOB); rcc_periph_clock_enable(RCC_AFIO); rcc_periph_clock_enable(RCC_CRC); @@ -67,6 +73,14 @@ void platform_init(void) gpio_set_mode(TDO_PORT, GPIO_MODE_INPUT, GPIO_CNF_INPUT_FLOAT, TDO_PIN); + if (rev == 1) { + /* Enable MCO Out on PA8*/ + RCC_CFGR &= ~(0xf << 24); + RCC_CFGR |= (RCC_CFGR_MCO_HSE << 24); + gpio_set_mode(GPIOA, GPIO_MODE_OUTPUT_50_MHZ, + GPIO_CNF_OUTPUT_ALTFN_PUSHPULL, GPIO8); + } + gpio_set(NRST_PORT,NRST_PIN); gpio_set_mode(NRST_PORT, GPIO_MODE_INPUT, GPIO_CNF_INPUT_PULL_UPDOWN, NRST_PIN); diff --git a/src/platforms/swlink/platform.h b/src/platforms/swlink/platform.h index 436dd24..e7dbe0a 100644 --- a/src/platforms/swlink/platform.h +++ b/src/platforms/swlink/platform.h @@ -3,6 +3,7 @@ * * Copyright (C) 2011 Black Sphere Technologies Ltd. * Written by Gareth McMullin + * Copyright (C) 2018 Uwe Bonnes (bon@elektron.ikp.physik.tu-darmstadt.de) * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -29,11 +30,11 @@ #include "timing_stm32.h" #include "version.h" -#define BOARD_IDENT "Black Magic Probe (SWLINK), (Firmware " FIRMWARE_VERSION ")" -#define BOARD_IDENT_DFU "Black Magic (Upgrade), STM8S Discovery, (Firmware " FIRMWARE_VERSION ")" -#define BOARD_IDENT_UPD "Black Magic (DFU Upgrade), STM8S Discovery, (Firmware " FIRMWARE_VERSION ")" -#define DFU_IDENT "Black Magic Firmware Upgrade (SWLINK)" -#define UPD_IFACE_STRING "@Internal Flash /0x08000000/8*001Kg" +#define BOARD_IDENT "Black Magic Probe (SWLINK), (Firmware " FIRMWARE_VERSION ")" +#define BOARD_IDENT_DFU "Black Magic (Upgrade), SWLINK, (Firmware " FIRMWARE_VERSION ")" +#define BOARD_IDENT_UPD "Black Magic (DFU Upgrade), SWLINK, (Firmware " FIRMWARE_VERSION ")" +#define DFU_IDENT "Black Magic Firmware Upgrade (SWLINK)" +#define UPD_IFACE_STRING "@Internal Flash /0x08000000/8*001Kg" /* Hardware definitions... */ #define TMS_PORT GPIOA @@ -128,10 +129,7 @@ int usbuart_debug_write(const char *buf, size_t len); #define SET_IDLE_STATE(state) {gpio_set_val(LED_PORT, LED_IDLE_RUN, state);} #define SET_ERROR_STATE(x) -static inline int platform_hwversion(void) -{ - return 0; -} +extern uint8_t detect_rev(void); /* Use newlib provided integer only stdio functions */ #define sscanf siscanf diff --git a/src/platforms/swlink/platform_common.c b/src/platforms/swlink/platform_common.c new file mode 100644 index 0000000..b1a3ad3 --- /dev/null +++ b/src/platforms/swlink/platform_common.c @@ -0,0 +1,75 @@ +/* + * This file is part of the Black Magic Debug project. + * + * Copyright (C) 2018 Uwe Bonnes (bon@elektron.ikp.physik.tu-darmstadt.de) + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +#include +#include +#include + +uint8_t detect_rev() +{ + /* Test connectivity between PB9 and PB10 needed for + * original ST software to implement SWIM. + * + * Return 0 for Stlink on STM8S Disco and 1 for Bluepill + */ + uint8_t rev = 0; + /* Enable Peripherals used by both debugger and DFU.*/ + rcc_periph_clock_enable(RCC_GPIOA); + rcc_periph_clock_enable(RCC_GPIOB); + rcc_periph_clock_enable(RCC_USB); + gpio_set_mode(GPIOB, GPIO_MODE_INPUT, + GPIO_CNF_INPUT_PULL_UPDOWN, GPIO9); + gpio_set(GPIOB, GPIO9); + gpio_set_mode(GPIOB, GPIO_MODE_OUTPUT_2_MHZ, + GPIO_CNF_OUTPUT_PUSHPULL, GPIO10); + while (!gpio_get(GPIOB, GPIO10)) + gpio_set(GPIOB, GPIO10); + while (gpio_get(GPIOB, GPIO10)) + gpio_clear(GPIOB, GPIO10); + /* Read PB9 as soon as we read PB10 low.*/ + if (gpio_get(GPIOB, GPIO9)) + rev = 1; + /* Release PB9/10 */ + gpio_set_mode(GPIOB, GPIO_MODE_INPUT, + GPIO_CNF_INPUT_FLOAT, GPIO9 | GPIO10); + gpio_set(GPIOB, GPIO9); + switch (rev) { + case 0: + gpio_set_mode(GPIOA, GPIO_MODE_OUTPUT_2_MHZ, + GPIO_CNF_OUTPUT_PUSHPULL, GPIO8); + break; + case 1: + rcc_periph_clock_enable(RCC_GPIOC); + gpio_set(GPIOC, GPIO13); /* LED on Blupill is active low!*/ + gpio_set_mode(GPIOC, GPIO_MODE_OUTPUT_2_MHZ, + GPIO_CNF_OUTPUT_PUSHPULL, GPIO13); + break; + } + /* Disconnect USB after reset: + * Pull USB_DP low. Device will reconnect automatically + * when USB is set up later, as Pull-Up is hard wired*/ + gpio_set_mode(GPIOA, GPIO_MODE_OUTPUT_2_MHZ, + GPIO_CNF_OUTPUT_OPENDRAIN, GPIO12); + gpio_clear(GPIOA, GPIO12); + rcc_periph_reset_pulse(RST_USB); + rcc_periph_clock_enable(RCC_USB); + + return rev; +} + diff --git a/src/platforms/swlink/usbdfu.c b/src/platforms/swlink/usbdfu.c index daf73f3..46ee39d 100644 --- a/src/platforms/swlink/usbdfu.c +++ b/src/platforms/swlink/usbdfu.c @@ -65,21 +65,6 @@ int main(void) systick_set_clocksource(STK_CSR_CLKSOURCE_AHB_DIV8); systick_set_reload(900000); - /* Handle USB disconnect/connect */ - /* Just in case: Disconnect USB cable by resetting USB Device - * and pulling USB_DP low - * Device will reconnect automatically as Pull-Up is hard wired*/ - rcc_periph_reset_pulse(RST_USB); - rcc_periph_clock_enable(RCC_USB); - rcc_periph_clock_enable(RCC_GPIOA); - gpio_clear(GPIOA, GPIO12); - gpio_set_mode(GPIOA, GPIO_MODE_OUTPUT_2_MHZ, - GPIO_CNF_OUTPUT_OPENDRAIN, GPIO12); - - /* Handle LED*/ - gpio_set_mode(GPIOA, GPIO_MODE_OUTPUT_2_MHZ, - GPIO_CNF_OUTPUT_PUSHPULL, GPIO8); - systick_interrupt_enable(); systick_counter_enable();