From db5e22a5b36e71619ee4492d8d9edbe9d73afb85 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?King=20K=C3=A9vin?= Date: Wed, 10 Mar 2021 14:15:04 +0100 Subject: [PATCH] application: include SWD utilities --- application.c | 51 +++++++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 47 insertions(+), 4 deletions(-) diff --git a/application.c b/application.c index 33982be..957dabd 100644 --- a/application.c +++ b/application.c @@ -1,8 +1,8 @@ -/** STM32F4 application example +/** SWJ (SWD + JTAG) finder * @file * @author King Kévin * @copyright SPDX-License-Identifier: GPL-3.0-or-later - * @date 2016-2020 + * @date 2016-2021 */ /* standard libraries */ @@ -32,6 +32,7 @@ #include "usb_cdcacm.h" // USB CDC ACM utilities #include "terminal.h" // handle the terminal interface #include "menu.h" // menu utilities +#include "swd.h" // SWD utilities /** watchdog period in ms */ #define WATCHDOG_PERIOD 10000 @@ -69,6 +70,36 @@ size_t putc(char c) // menu commands +static void command_swd_scan(void* argument) +{ + (void)argument; // we won't use the argument + printf("SWD target DPIDR: "); + uint32_t data; // data to read/write over SWD + enum swd_ack_e ack; // SWD acknowledge response + swd_line_reset(); // put target in reset state + swd_jtag_to_swd(); // put target SWJ in SWD mode + swd_line_reset(); // put target in reset state + swd_idle_cycles(2); // idle before packer request + swd_packet_request(false, SWD_A_DP_DPIDR, true); // request DPIDR + swd_turnaround(1); // switch from writing to reading + ack = swd_acknowledge_response(); // get ack + if (SWD_ACK_OK != ack) { + printf("ack error\n"); + return; + } + if (!swd_read(&data)) { + printf("parity error\n"); + return; + } + swd_turnaround(1); // switch from reading to writing + printf("0x%08x ", data); + if (data & 0x1) { + printf("(designer: %03x/%s, version: %u, part number: 0x%02x/%s, revision %u)\n", (data >> 1) & 0x3ff, swd_jep106_manufacturer((data >> 8) & 0x0f, (data >> 1) & 0x7f), (data >> 12) & 0x0f, (data >> 20) & 0xff, swd_dpidr_partno((data >> 1) & 0x3ff, (data >> 20) & 0xff), (data >> 28) & 0x0f); + } else { + printf("(invalid: RAO != 1)\n"); + } +} + /** display available commands * @param[in] argument no argument required */ @@ -305,7 +336,7 @@ static const struct menu_command_t menu_commands[] = { .command_handler = &command_reset, }, { - .shortcut = 's', + .shortcut = 'S', .name = "system", .command_description = "reboot into system memory", .argument = MENU_ARGUMENT_NONE, @@ -320,6 +351,14 @@ static const struct menu_command_t menu_commands[] = { .argument_description = NULL, .command_handler = &command_bootloader, }, + { + .shortcut = 's', + .name = "scan", + .command_description = "scan SWD device", + .argument = MENU_ARGUMENT_NONE, + .argument_description = NULL, + .command_handler = &command_swd_scan, + }, }; static void command_help(void* argument) @@ -374,7 +413,7 @@ void main(void) board_setup(); // setup board uart_setup(); // setup USART (for printing) usb_cdcacm_setup(); // setup USB CDC ACM (for printing) - puts("\nwelcome to the CuVoodoo STM32F4 example firmware\n"); // print welcome message + puts("\nwelcome to the CuVoodoo SWJ finder\n"); // print welcome message #if DEBUG // show reset cause @@ -454,6 +493,10 @@ void main(void) // important: do not re-enable backup_domain_write_protect, since this will prevent clearing flags (but RTC registers do not need to be unlocked) puts("OK\n"); + puts("setup SWD: "); + swd_setup(100000); // setup SWD clock to 100 KHz, slow enough for any target and loose connection + puts("OK\n"); + // setup terminal terminal_prefix = ""; // set default prefix terminal_process = &process_command; // set central function to process commands