Further split-up of DFU bootloader.
This commit is contained in:
parent
14e5e8b0b6
commit
55f161208d
|
@ -23,7 +23,7 @@ all: blackmagic.bin blackmagic_dfu.bin blackmagic_dfu.hex
|
||||||
blackmagic.bin: blackmagic
|
blackmagic.bin: blackmagic
|
||||||
$(OBJCOPY) -O binary $^ $@
|
$(OBJCOPY) -O binary $^ $@
|
||||||
|
|
||||||
blackmagic_dfu: usbdfu.o
|
blackmagic_dfu: usbdfu.o dfucore.o dfu_f4.o
|
||||||
$(CC) $^ -o $@ $(LDFLAGS_BOOT)
|
$(CC) $^ -o $@ $(LDFLAGS_BOOT)
|
||||||
|
|
||||||
blackmagic_dfu.bin: blackmagic_dfu
|
blackmagic_dfu.bin: blackmagic_dfu
|
||||||
|
|
|
@ -36,7 +36,9 @@
|
||||||
#define CDCACM_PACKET_SIZE 64
|
#define CDCACM_PACKET_SIZE 64
|
||||||
#define PLATFORM_HAS_TRACESWO
|
#define PLATFORM_HAS_TRACESWO
|
||||||
#define BOARD_IDENT "Black Magic Probe (F4Discovery), (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
#define BOARD_IDENT "Black Magic Probe (F4Discovery), (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
||||||
|
#define BOARD_IDENT_DFU "Black Magic (Upgrade) for F4Discovery, (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
||||||
#define DFU_IDENT "Black Magic Firmware Upgrade (F4Discovery"
|
#define DFU_IDENT "Black Magic Firmware Upgrade (F4Discovery"
|
||||||
|
#define IFACE_STRING "@Internal Flash /0x08000000/1*016Ka,3*016Kg,1*064Kg,7*128Kg"
|
||||||
|
|
||||||
extern usbd_device *usbdev;
|
extern usbd_device *usbdev;
|
||||||
#define CDCACM_GDB_ENDPOINT 1
|
#define CDCACM_GDB_ENDPOINT 1
|
||||||
|
|
|
@ -23,7 +23,7 @@ all: blackmagic.bin blackmagic_dfu.bin blackmagic_dfu.hex
|
||||||
blackmagic.bin: blackmagic
|
blackmagic.bin: blackmagic
|
||||||
$(OBJCOPY) -O binary $^ $@
|
$(OBJCOPY) -O binary $^ $@
|
||||||
|
|
||||||
blackmagic_dfu: usbdfu.o
|
blackmagic_dfu: usbdfu.o dfucore.o dfu_f1.o
|
||||||
$(CC) $^ -o $@ $(LDFLAGS_BOOT)
|
$(CC) $^ -o $@ $(LDFLAGS_BOOT)
|
||||||
|
|
||||||
blackmagic_dfu.bin: blackmagic_dfu
|
blackmagic_dfu.bin: blackmagic_dfu
|
||||||
|
|
|
@ -36,7 +36,9 @@
|
||||||
#define CDCACM_PACKET_SIZE 64
|
#define CDCACM_PACKET_SIZE 64
|
||||||
#define PLATFORM_HAS_TRACESWO
|
#define PLATFORM_HAS_TRACESWO
|
||||||
#define BOARD_IDENT "Black Magic Probe, (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
#define BOARD_IDENT "Black Magic Probe, (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
||||||
|
#define BOARD_IDENT_DFU "Black Magic Probe (Upgrade), (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
||||||
#define DFU_IDENT "Black Magic Firmware Upgrade"
|
#define DFU_IDENT "Black Magic Firmware Upgrade"
|
||||||
|
#define DFU_IFACE_STRING "@Internal Flash /0x08000000/8*001Ka,120*001Kg"
|
||||||
|
|
||||||
extern usbd_device *usbdev;
|
extern usbd_device *usbdev;
|
||||||
#define CDCACM_GDB_ENDPOINT 1
|
#define CDCACM_GDB_ENDPOINT 1
|
||||||
|
|
|
@ -21,7 +21,7 @@ all: blackmagic.bin blackmagic_dfu.bin blackmagic_dfu.hex
|
||||||
blackmagic.bin: blackmagic
|
blackmagic.bin: blackmagic
|
||||||
$(OBJCOPY) -O binary $^ $@
|
$(OBJCOPY) -O binary $^ $@
|
||||||
|
|
||||||
blackmagic_dfu: usbdfu.o
|
blackmagic_dfu: usbdfu.o dfucore.o dfu_f1.o
|
||||||
$(CC) $^ -o $@ $(LDFLAGS_BOOT)
|
$(CC) $^ -o $@ $(LDFLAGS_BOOT)
|
||||||
|
|
||||||
blackmagic_dfu.bin: blackmagic_dfu
|
blackmagic_dfu.bin: blackmagic_dfu
|
||||||
|
|
|
@ -35,7 +35,9 @@
|
||||||
#define INLINE_GPIO
|
#define INLINE_GPIO
|
||||||
#define CDCACM_PACKET_SIZE 64
|
#define CDCACM_PACKET_SIZE 64
|
||||||
#define BOARD_IDENT "Black Magic Probe (STLINK), (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
#define BOARD_IDENT "Black Magic Probe (STLINK), (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
||||||
|
#define BOARD_IDENT_DFU "Black Magic (Upgrade) for STLink/Discovery, (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
||||||
#define DFU_IDENT "Black Magic Firmware Upgrade (STLINK)"
|
#define DFU_IDENT "Black Magic Firmware Upgrade (STLINK)"
|
||||||
|
#define DFU_IFACE_STRING "@Internal Flash /0x08000000/8*001Ka,56*001Kg"
|
||||||
|
|
||||||
extern usbd_device *usbdev;
|
extern usbd_device *usbdev;
|
||||||
#define CDCACM_GDB_ENDPOINT 1
|
#define CDCACM_GDB_ENDPOINT 1
|
||||||
|
|
|
@ -0,0 +1,88 @@
|
||||||
|
/*
|
||||||
|
* This file is part of the Black Magic Debug project.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2013 Gareth McMullin <gareth@blacksphere.co.nz>
|
||||||
|
*
|
||||||
|
* 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 <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
#include <libopencm3/stm32/f1/flash.h>
|
||||||
|
#include <libopencm3/cm3/scb.h>
|
||||||
|
#include "usbdfu.h"
|
||||||
|
|
||||||
|
#define FLASH_OBP_RDP 0x1FFFF800
|
||||||
|
#define FLASH_OBP_WRP10 0x1FFFF808
|
||||||
|
|
||||||
|
#define FLASH_OBP_RDP_KEY 0x5aa5
|
||||||
|
|
||||||
|
#if defined (STM32_CAN)
|
||||||
|
# define FLASHBLOCKSIZE 2048
|
||||||
|
#else
|
||||||
|
# define FLASHBLOCKSIZE 1024
|
||||||
|
#endif
|
||||||
|
|
||||||
|
static uint32_t last_erased_page = 0xffffffff;
|
||||||
|
|
||||||
|
void dfu_check_and_do_sector_erase(uint32_t sector)
|
||||||
|
{
|
||||||
|
sector &= (~(FLASHBLOCKSIZE - 1));
|
||||||
|
if (sector != last_erased_page) {
|
||||||
|
flash_erase_page(sector);
|
||||||
|
last_erased_page = sector;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void dfu_flash_program_buffer(uint32_t baseaddr, void *buf, int len)
|
||||||
|
{
|
||||||
|
for(int i = 0; i < len; i += 2)
|
||||||
|
flash_program_half_word(baseaddr + i,
|
||||||
|
*(u16*)(buf+i));
|
||||||
|
}
|
||||||
|
|
||||||
|
uint32_t dfu_poll_timeout(uint8_t cmd, uint32_t addr, uint16_t blocknum)
|
||||||
|
{
|
||||||
|
(void)cmd;
|
||||||
|
(void)addr;
|
||||||
|
(void)blocknum;
|
||||||
|
return 100;
|
||||||
|
}
|
||||||
|
|
||||||
|
void dfu_protect_enable(void)
|
||||||
|
{
|
||||||
|
if ((FLASH_WRPR & 0x03) != 0x00) {
|
||||||
|
flash_unlock();
|
||||||
|
FLASH_CR = 0;
|
||||||
|
flash_erase_option_bytes();
|
||||||
|
flash_program_option_bytes(FLASH_OBP_RDP, FLASH_OBP_RDP_KEY);
|
||||||
|
/* CL Device: Protect 2 bits with (2 * 2k pages each)*/
|
||||||
|
/* MD Device: Protect 2 bits with (4 * 1k pages each)*/
|
||||||
|
flash_program_option_bytes(FLASH_OBP_WRP10, 0x03FC);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void dfu_jump_app_if_valid(void)
|
||||||
|
{
|
||||||
|
/* Boot the application if it's valid */
|
||||||
|
if((*(volatile u32*)APP_ADDRESS & 0x2FFE0000) == 0x20000000) {
|
||||||
|
/* Set vector table base address */
|
||||||
|
SCB_VTOR = APP_ADDRESS & 0x1FFFFF; /* Max 2 MByte Flash*/
|
||||||
|
/* Initialise master stack pointer */
|
||||||
|
asm volatile ("msr msp, %0"::"g"
|
||||||
|
(*(volatile u32*)APP_ADDRESS));
|
||||||
|
/* Jump to application */
|
||||||
|
(*(void(**)())(APP_ADDRESS + 4))();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -0,0 +1,103 @@
|
||||||
|
/*
|
||||||
|
* This file is part of the Black Magic Debug project.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2013 Gareth McMullin <gareth@blacksphere.co.nz>
|
||||||
|
*
|
||||||
|
* 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 <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#if defined(STM32F2)
|
||||||
|
# include <libopencm3/stm32/f2/flash.h>
|
||||||
|
#elif defined(STM32F4)
|
||||||
|
# include <libopencm3/stm32/f4/flash.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#include "usbdfu.h"
|
||||||
|
|
||||||
|
static u32 sector_addr[] = {0x8000000, 0x8004000, 0x8008000, 0x800c000,
|
||||||
|
0x8010000, 0x8020000, 0x8040000, 0x8060000,
|
||||||
|
0x8080000, 0x80a0000, 0x80c0000, 0x80e0000,
|
||||||
|
0x8100000, 0};
|
||||||
|
static u16 sector_erase_time[12]= {500, 500, 500, 500,
|
||||||
|
1100,
|
||||||
|
2600, 2600, 2600, 2600, 2600, 2600, 2600};
|
||||||
|
static u8 sector_num = 0xff;
|
||||||
|
|
||||||
|
/* Find the sector number for a given address*/
|
||||||
|
static void get_sector_num(u32 addr)
|
||||||
|
{
|
||||||
|
int i = 0;
|
||||||
|
while(sector_addr[i+1]) {
|
||||||
|
if (addr < sector_addr[i+1])
|
||||||
|
break;
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
if (!sector_addr[i])
|
||||||
|
return;
|
||||||
|
sector_num = i;
|
||||||
|
}
|
||||||
|
|
||||||
|
void dfu_check_and_do_sector_erase(uint32_t addr)
|
||||||
|
{
|
||||||
|
if(addr == sector_addr[sector_num]) {
|
||||||
|
flash_erase_sector((sector_num & 0x1f)<<3, FLASH_PROGRAM_X32);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void dfu_flash_program_buffer(uint32_t baseaddr, void *buf, int len)
|
||||||
|
{
|
||||||
|
for(int i = 0; i < len; i += 4)
|
||||||
|
flash_program_word(baseaddr + i,
|
||||||
|
*(u32*)(buf+i),
|
||||||
|
FLASH_PROGRAM_X32);
|
||||||
|
}
|
||||||
|
|
||||||
|
uint32_t dfu_poll_timeout(uint8_t cmd, uint32_t addr, uint16_t blocknum)
|
||||||
|
{
|
||||||
|
/* Erase for big pages on STM2/4 needs "long" time
|
||||||
|
Try not to hit USB timeouts*/
|
||||||
|
if ((blocknum == 0) && (cmd == CMD_ERASE)) {
|
||||||
|
get_sector_num(addr);
|
||||||
|
if(addr == sector_addr[sector_num])
|
||||||
|
return sector_erase_time[sector_num];
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Programming 256 word with 100 us(max) per word*/
|
||||||
|
return 26;
|
||||||
|
}
|
||||||
|
|
||||||
|
void dfu_protect_enable(void)
|
||||||
|
{
|
||||||
|
if ((FLASH_OPTCR & 0x10000) != 0) {
|
||||||
|
flash_program_option_bytes(FLASH_OPTCR & ~0x10000);
|
||||||
|
flash_lock_option_bytes();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void dfu_jump_app_if_valid(void)
|
||||||
|
{
|
||||||
|
/* Boot the application if it's valid */
|
||||||
|
/* Vector table may be anywhere in 128 kByte RAM
|
||||||
|
CCM not handled*/
|
||||||
|
if((*(volatile u32*)APP_ADDRESS & 0x2FFC0000) == 0x20000000) {
|
||||||
|
/* Set vector table base address */
|
||||||
|
SCB_VTOR = APP_ADDRESS & 0x1FFFFF; /* Max 2 MByte Flash*/
|
||||||
|
/* Initialise master stack pointer */
|
||||||
|
asm volatile ("msr msp, %0"::"g"
|
||||||
|
(*(volatile u32*)APP_ADDRESS));
|
||||||
|
/* Jump to application */
|
||||||
|
(*(void(**)())(APP_ADDRESS + 4))();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -17,10 +17,21 @@
|
||||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include "platform.h"
|
||||||
|
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
#if defined(STM32F1)
|
||||||
|
# include <libopencm3/stm32/f1/flash.h>
|
||||||
|
#elif defined(STM32F2)
|
||||||
|
# include <libopencm3/stm32/f2/flash.h>
|
||||||
|
#elif defined(STM32F4)
|
||||||
|
# include <libopencm3/stm32/f4/flash.h>
|
||||||
|
#endif
|
||||||
#include <libopencm3/usb/usbd.h>
|
#include <libopencm3/usb/usbd.h>
|
||||||
#include <libopencm3/usb/dfu.h>
|
#include <libopencm3/usb/dfu.h>
|
||||||
|
|
||||||
|
#include "usbdfu.h"
|
||||||
|
|
||||||
/* Commands sent with wBlockNum == 0 as per ST implementation. */
|
/* Commands sent with wBlockNum == 0 as per ST implementation. */
|
||||||
#define CMD_SETADDR 0x21
|
#define CMD_SETADDR 0x21
|
||||||
#define CMD_ERASE 0x41
|
#define CMD_ERASE 0x41
|
||||||
|
@ -29,6 +40,8 @@ usbd_device *usbdev;
|
||||||
/* We need a special large control buffer for this device: */
|
/* We need a special large control buffer for this device: */
|
||||||
u8 usbd_control_buffer[1024];
|
u8 usbd_control_buffer[1024];
|
||||||
|
|
||||||
|
static u32 max_address;
|
||||||
|
|
||||||
static enum dfu_state usbdfu_state = STATE_DFU_IDLE;
|
static enum dfu_state usbdfu_state = STATE_DFU_IDLE;
|
||||||
|
|
||||||
static char *get_dev_unique_id(char *serial_no);
|
static char *get_dev_unique_id(char *serial_no);
|
||||||
|
@ -106,10 +119,10 @@ static char serial_no[9];
|
||||||
|
|
||||||
static const char *usb_strings[] = {
|
static const char *usb_strings[] = {
|
||||||
"Black Sphere Technologies",
|
"Black Sphere Technologies",
|
||||||
PRODUCT_STRING,
|
BOARD_IDENT_DFU,
|
||||||
serial_no,
|
serial_no,
|
||||||
/* This string is used by ST Microelectronics' DfuSe utility */
|
/* This string is used by ST Microelectronics' DfuSe utility */
|
||||||
IFACE_STRING,
|
DFU_IFACE_STRING,
|
||||||
};
|
};
|
||||||
|
|
||||||
static u8 usbdfu_getstatus(u32 *bwPollTimeout)
|
static u8 usbdfu_getstatus(u32 *bwPollTimeout)
|
||||||
|
@ -117,7 +130,7 @@ static u8 usbdfu_getstatus(u32 *bwPollTimeout)
|
||||||
switch(usbdfu_state) {
|
switch(usbdfu_state) {
|
||||||
case STATE_DFU_DNLOAD_SYNC:
|
case STATE_DFU_DNLOAD_SYNC:
|
||||||
usbdfu_state = STATE_DFU_DNBUSY;
|
usbdfu_state = STATE_DFU_DNBUSY;
|
||||||
*bwPollTimeout = poll_timeout(prog.buf[0],
|
*bwPollTimeout = dfu_poll_timeout(prog.buf[0],
|
||||||
*(u32 *)(prog.buf + 1),
|
*(u32 *)(prog.buf + 1),
|
||||||
prog.blocknum);
|
prog.blocknum);
|
||||||
return DFU_STATUS_OK;
|
return DFU_STATUS_OK;
|
||||||
|
@ -151,7 +164,7 @@ usbdfu_getstatus_complete(usbd_device *dev, struct usb_setup_data *req)
|
||||||
}
|
}
|
||||||
switch(prog.buf[0]) {
|
switch(prog.buf[0]) {
|
||||||
case CMD_ERASE:
|
case CMD_ERASE:
|
||||||
check_and_do_sector_erase(addr);
|
dfu_check_and_do_sector_erase(addr);
|
||||||
case CMD_SETADDR:
|
case CMD_SETADDR:
|
||||||
prog.addr = addr;
|
prog.addr = addr;
|
||||||
}
|
}
|
||||||
|
@ -159,7 +172,7 @@ usbdfu_getstatus_complete(usbd_device *dev, struct usb_setup_data *req)
|
||||||
u32 baseaddr = prog.addr +
|
u32 baseaddr = prog.addr +
|
||||||
((prog.blocknum - 2) *
|
((prog.blocknum - 2) *
|
||||||
dfu_function.wTransferSize);
|
dfu_function.wTransferSize);
|
||||||
flash_program_buffer(baseaddr, prog.buf, prog.len);
|
dfu_flash_program_buffer(baseaddr, prog.buf, prog.len);
|
||||||
}
|
}
|
||||||
flash_lock();
|
flash_lock();
|
||||||
|
|
||||||
|
@ -170,7 +183,7 @@ usbdfu_getstatus_complete(usbd_device *dev, struct usb_setup_data *req)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
case STATE_DFU_MANIFEST:
|
case STATE_DFU_MANIFEST:
|
||||||
detach();
|
dfu_detach();
|
||||||
return; /* Will never return */
|
return; /* Will never return */
|
||||||
default:
|
default:
|
||||||
return;
|
return;
|
||||||
|
@ -236,3 +249,56 @@ static int usbdfu_control_request(usbd_device *dev,
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void dfu_init(const usbd_driver *driver)
|
||||||
|
{
|
||||||
|
get_dev_unique_id(serial_no);
|
||||||
|
|
||||||
|
usbdev = usbd_init(driver, &dev, &config, usb_strings, 4);
|
||||||
|
usbd_set_control_buffer_size(usbdev, sizeof(usbd_control_buffer));
|
||||||
|
usbd_register_control_callback(usbdev,
|
||||||
|
USB_REQ_TYPE_CLASS | USB_REQ_TYPE_INTERFACE,
|
||||||
|
USB_REQ_TYPE_TYPE | USB_REQ_TYPE_RECIPIENT,
|
||||||
|
usbdfu_control_request);
|
||||||
|
}
|
||||||
|
|
||||||
|
void dfu_main(void)
|
||||||
|
{
|
||||||
|
while (1)
|
||||||
|
usbd_poll(usbdev);
|
||||||
|
}
|
||||||
|
|
||||||
|
static char *get_dev_unique_id(char *s)
|
||||||
|
{
|
||||||
|
#if defined(STM32F4) || defined(STM32F2)
|
||||||
|
#define UNIQUE_SERIAL_R 0x1FFF7A10
|
||||||
|
#define FLASH_SIZE_R 0x1fff7A22
|
||||||
|
#elif defined(STM32F3)
|
||||||
|
#define UNIQUE_SERIAL_R 0x1FFFF7AC
|
||||||
|
#define FLASH_SIZE_R 0x1fff77cc
|
||||||
|
#elif defined(STM32L1)
|
||||||
|
#define UNIQUE_SERIAL_R 0x1ff80050
|
||||||
|
#define FLASH_SIZE_R 0x1FF8004C
|
||||||
|
#else
|
||||||
|
#define UNIQUE_SERIAL_R 0x1FFFF7E8;
|
||||||
|
#define FLASH_SIZE_R 0x1ffff7e0
|
||||||
|
#endif
|
||||||
|
volatile uint32_t *unique_id_p = (volatile uint32_t *)UNIQUE_SERIAL_R;
|
||||||
|
uint32_t unique_id = *unique_id_p +
|
||||||
|
*(unique_id_p + 1) +
|
||||||
|
*(unique_id_p + 2);
|
||||||
|
int i;
|
||||||
|
|
||||||
|
/* Calculated the upper flash limit from the exported data
|
||||||
|
in theparameter block*/
|
||||||
|
max_address = (*(u32 *) FLASH_SIZE_R) <<10;
|
||||||
|
/* Fetch serial number from chip's unique ID */
|
||||||
|
for(i = 0; i < 8; i++) {
|
||||||
|
s[7-i] = ((unique_id >> (4*i)) & 0xF) + '0';
|
||||||
|
}
|
||||||
|
for(i = 0; i < 8; i++)
|
||||||
|
if(s[i] > '9')
|
||||||
|
s[i] += 'A' - '9' - 1;
|
||||||
|
s[8] = 0;
|
||||||
|
|
||||||
|
return s;
|
||||||
|
}
|
||||||
|
|
|
@ -21,27 +21,9 @@
|
||||||
#include <libopencm3/cm3/systick.h>
|
#include <libopencm3/cm3/systick.h>
|
||||||
#include <libopencm3/stm32/rcc.h>
|
#include <libopencm3/stm32/rcc.h>
|
||||||
#include <libopencm3/stm32/gpio.h>
|
#include <libopencm3/stm32/gpio.h>
|
||||||
#if defined(STM32F1)
|
|
||||||
#include <libopencm3/stm32/f1/flash.h>
|
|
||||||
#elif defined(STM32F2)
|
|
||||||
#include <libopencm3/stm32/f2/flash.h>
|
|
||||||
#elif defined(STM32F4)
|
|
||||||
#include <libopencm3/stm32/f4/flash.h>
|
|
||||||
#else
|
|
||||||
#warning "Unhandled STM32 family"
|
|
||||||
#endif
|
|
||||||
#include <libopencm3/cm3/scb.h>
|
#include <libopencm3/cm3/scb.h>
|
||||||
|
|
||||||
#define FLASH_OBP_RDP 0x1FFFF800
|
#include "usbdfu.h"
|
||||||
#define FLASH_OBP_WRP10 0x1FFFF808
|
|
||||||
|
|
||||||
#define FLASH_OBP_RDP_KEY 0x5aa5
|
|
||||||
|
|
||||||
#if defined (STM32_CAN)
|
|
||||||
#define FLASHBLOCKSIZE 2048
|
|
||||||
#else
|
|
||||||
#define FLASHBLOCKSIZE 1024
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if defined(DISCOVERY_STLINK)
|
#if defined(DISCOVERY_STLINK)
|
||||||
uint8_t rev;
|
uint8_t rev;
|
||||||
|
@ -86,119 +68,7 @@ int stlink_test_nrst(void) {
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
static u32 max_address;
|
void dfu_detach(void)
|
||||||
#if defined (STM32F4)
|
|
||||||
#define APP_ADDRESS 0x08010000
|
|
||||||
static u32 sector_addr[] = {0x8000000, 0x8004000, 0x8008000, 0x800c000,
|
|
||||||
0x8010000, 0x8020000, 0x8040000, 0x8060000,
|
|
||||||
0x8080000, 0x80a0000, 0x80c0000, 0x80e0000,
|
|
||||||
0x8100000, 0};
|
|
||||||
u16 sector_erase_time[12]= {500, 500, 500, 500,
|
|
||||||
1100,
|
|
||||||
2600, 2600, 2600, 2600, 2600, 2600, 2600};
|
|
||||||
u8 sector_num = 0xff;
|
|
||||||
/* Find the sector number for a given address*/
|
|
||||||
void get_sector_num(u32 addr)
|
|
||||||
{
|
|
||||||
int i = 0;
|
|
||||||
while(sector_addr[i+1]) {
|
|
||||||
if (addr < sector_addr[i+1])
|
|
||||||
break;
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
if (!sector_addr[i])
|
|
||||||
return;
|
|
||||||
sector_num = i;
|
|
||||||
}
|
|
||||||
|
|
||||||
void check_and_do_sector_erase(u32 addr)
|
|
||||||
{
|
|
||||||
if(addr == sector_addr[sector_num]) {
|
|
||||||
flash_erase_sector((sector_num & 0x1f)<<3, FLASH_PROGRAM_X32);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
#define APP_ADDRESS 0x08002000
|
|
||||||
static uint32_t last_erased_page=0xffffffff;
|
|
||||||
void check_and_do_sector_erase(u32 sector)
|
|
||||||
{
|
|
||||||
sector &= (~(FLASHBLOCKSIZE-1));
|
|
||||||
if (sector != last_erased_page) {
|
|
||||||
flash_erase_page(sector);
|
|
||||||
last_erased_page = sector;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if defined(BLACKMAGIC)
|
|
||||||
# define PRODUCT_STRING \
|
|
||||||
"Black Magic Probe (Upgrade), (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
|
||||||
#elif defined(DISCOVERY_STLINK)
|
|
||||||
# define PRODUCT_STRING \
|
|
||||||
"Black Magic (Upgrade) for STLink/Discovery, (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
|
||||||
#elif defined(STM32_CAN)
|
|
||||||
# define PRODUCT_STRING \
|
|
||||||
"Black Magic (Upgrade) for STM32_CAN, (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
|
||||||
#elif defined(F4DISCOVERY)
|
|
||||||
# define PRODUCT_STRING \
|
|
||||||
"Black Magic (Upgrade) for F4Discovery, (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
|
||||||
#elif defined(USPS_F407)
|
|
||||||
# define PRODUCT_STRING \
|
|
||||||
"Black Magic (Upgrade) for USPS_F407, (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
|
||||||
#else
|
|
||||||
# warning "Unhandled board"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/* This string is used by ST Microelectronics' DfuSe utility */
|
|
||||||
#if defined(BLACKMAGIC)
|
|
||||||
# define IFACE_STRING "@Internal Flash /0x08000000/8*001Ka,120*001Kg"
|
|
||||||
#elif defined(DISCOVERY_STLINK)
|
|
||||||
# define IFACE_STRING "@Internal Flash /0x08000000/8*001Ka,56*001Kg"
|
|
||||||
#elif defined(STM32_CAN)
|
|
||||||
# define IFACE_STRING "@Internal Flash /0x08000000/4*002Ka,124*002Kg"
|
|
||||||
#elif defined(F4DISCOVERY) || defined(USPS_F407)
|
|
||||||
# define IFACE_STRING "@Internal Flash /0x08000000/1*016Ka,3*016Kg,1*064Kg,7*128Kg"
|
|
||||||
#else
|
|
||||||
# warning "Unhandled board"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
static u32 poll_timeout(uint8_t cmd, uint32_t addr, uint16_t blocknum)
|
|
||||||
{
|
|
||||||
#if defined(STM32F4)
|
|
||||||
/* Erase for big pages on STM2/4 needs "long" time
|
|
||||||
Try not to hit USB timeouts*/
|
|
||||||
if ((blocknum == 0) && (cmd == CMD_ERASE)) {
|
|
||||||
get_sector_num(addr);
|
|
||||||
if(addr == sector_addr[sector_num])
|
|
||||||
return sector_erase_time[sector_num];
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Programming 256 word with 100 us(max) per word*/
|
|
||||||
return 26;
|
|
||||||
#else
|
|
||||||
(void)cmd;
|
|
||||||
(void)addr;
|
|
||||||
(void)blocknum;
|
|
||||||
return 100;
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
static void flash_program_buffer(uint32_t baseaddr, void *buf, int len)
|
|
||||||
{
|
|
||||||
int i;
|
|
||||||
#if defined (STM32F4)
|
|
||||||
for(i = 0; i < len; i += 4)
|
|
||||||
flash_program_word(baseaddr + i,
|
|
||||||
*(u32*)(buf+i),
|
|
||||||
FLASH_PROGRAM_X32);
|
|
||||||
#else
|
|
||||||
for(i = 0; i < len; i += 2)
|
|
||||||
flash_program_half_word(baseaddr + i,
|
|
||||||
*(u16*)(buf+i));
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
static void detach(void)
|
|
||||||
{
|
{
|
||||||
#if defined (DISCOVERY_STLINK)
|
#if defined (DISCOVERY_STLINK)
|
||||||
/* Disconnect USB cable by resetting USB Device
|
/* Disconnect USB cable by resetting USB Device
|
||||||
|
@ -216,8 +86,6 @@ static void detach(void)
|
||||||
scb_reset_system();
|
scb_reset_system();
|
||||||
}
|
}
|
||||||
|
|
||||||
#include "dfucore.c"
|
|
||||||
|
|
||||||
int main(void)
|
int main(void)
|
||||||
{
|
{
|
||||||
/* Check the force bootloader pin*/
|
/* Check the force bootloader pin*/
|
||||||
|
@ -247,40 +115,10 @@ int main(void)
|
||||||
rcc_peripheral_enable_clock(&RCC_APB2ENR, RCC_APB2ENR_IOPBEN);
|
rcc_peripheral_enable_clock(&RCC_APB2ENR, RCC_APB2ENR_IOPBEN);
|
||||||
if(gpio_get(GPIOB, GPIO12)) {
|
if(gpio_get(GPIOB, GPIO12)) {
|
||||||
#endif
|
#endif
|
||||||
/* Boot the application if it's valid */
|
dfu_jump_app_if_valid();
|
||||||
#if defined (STM32F4)
|
|
||||||
/* Vector table may be anywhere in 128 kByte RAM
|
|
||||||
CCM not handled*/
|
|
||||||
if((*(volatile u32*)APP_ADDRESS & 0x2FFC0000) == 0x20000000) {
|
|
||||||
#else
|
|
||||||
if((*(volatile u32*)APP_ADDRESS & 0x2FFE0000) == 0x20000000) {
|
|
||||||
#endif
|
|
||||||
/* Set vector table base address */
|
|
||||||
SCB_VTOR = APP_ADDRESS & 0x1FFFFF; /* Max 2 MByte Flash*/
|
|
||||||
/* Initialise master stack pointer */
|
|
||||||
asm volatile ("msr msp, %0"::"g"
|
|
||||||
(*(volatile u32*)APP_ADDRESS));
|
|
||||||
/* Jump to application */
|
|
||||||
(*(void(**)())(APP_ADDRESS + 4))();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#if defined (STM32F4)
|
dfu_protect_enable();
|
||||||
if ((FLASH_OPTCR & 0x10000) != 0) {
|
|
||||||
flash_program_option_bytes(FLASH_OPTCR & ~0x10000);
|
|
||||||
flash_lock_option_bytes();
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
if ((FLASH_WRPR & 0x03) != 0x00) {
|
|
||||||
flash_unlock();
|
|
||||||
FLASH_CR = 0;
|
|
||||||
flash_erase_option_bytes();
|
|
||||||
flash_program_option_bytes(FLASH_OBP_RDP, FLASH_OBP_RDP_KEY);
|
|
||||||
/* CL Device: Protect 2 bits with (2 * 2k pages each)*/
|
|
||||||
/* MD Device: Protect 2 bits with (4 * 1k pages each)*/
|
|
||||||
flash_program_option_bytes(FLASH_OBP_WRP10, 0x03FC);
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/* Set up clock*/
|
/* Set up clock*/
|
||||||
#if defined (F4DISCOVERY) || defined(USPS_F407)
|
#if defined (F4DISCOVERY) || defined(USPS_F407)
|
||||||
|
@ -316,7 +154,6 @@ int main(void)
|
||||||
#endif
|
#endif
|
||||||
systick_interrupt_enable();
|
systick_interrupt_enable();
|
||||||
systick_counter_enable();
|
systick_counter_enable();
|
||||||
get_dev_unique_id(serial_no);
|
|
||||||
|
|
||||||
/* Handle LEDs */
|
/* Handle LEDs */
|
||||||
#if defined(F4DISCOVERY)
|
#if defined(F4DISCOVERY)
|
||||||
|
@ -345,8 +182,7 @@ int main(void)
|
||||||
rcc_peripheral_enable_clock(&RCC_APB2ENR, RCC_APB2ENR_IOPAEN);
|
rcc_peripheral_enable_clock(&RCC_APB2ENR, RCC_APB2ENR_IOPAEN);
|
||||||
rcc_peripheral_enable_clock(&RCC_AHBENR, RCC_AHBENR_OTGFSEN);
|
rcc_peripheral_enable_clock(&RCC_AHBENR, RCC_AHBENR_OTGFSEN);
|
||||||
rcc_peripheral_enable_clock(&RCC_APB2ENR, RCC_APB2ENR_IOPBEN);
|
rcc_peripheral_enable_clock(&RCC_APB2ENR, RCC_APB2ENR_IOPBEN);
|
||||||
usbdev = usbd_init(&stm32f107_usb_driver,
|
dfu_init(&stm32f107_usb_driver);
|
||||||
&dev, &config, usb_strings, 4);
|
|
||||||
#elif defined(STM32F2)||defined(STM32F4)
|
#elif defined(STM32F2)||defined(STM32F4)
|
||||||
rcc_peripheral_enable_clock(&RCC_AHB1ENR, RCC_AHB1ENR_IOPAEN);
|
rcc_peripheral_enable_clock(&RCC_AHB1ENR, RCC_AHB1ENR_IOPAEN);
|
||||||
rcc_peripheral_enable_clock(&RCC_AHB2ENR, RCC_AHB2ENR_OTGFSEN);
|
rcc_peripheral_enable_clock(&RCC_AHB2ENR, RCC_AHB2ENR_OTGFSEN);
|
||||||
|
@ -355,17 +191,10 @@ int main(void)
|
||||||
gpio_mode_setup(GPIOA, GPIO_MODE_AF, GPIO_PUPD_NONE,
|
gpio_mode_setup(GPIOA, GPIO_MODE_AF, GPIO_PUPD_NONE,
|
||||||
GPIO9 | GPIO10 | GPIO11 | GPIO12);
|
GPIO9 | GPIO10 | GPIO11 | GPIO12);
|
||||||
gpio_set_af(GPIOA, GPIO_AF10, GPIO9 | GPIO10| GPIO11 | GPIO12);
|
gpio_set_af(GPIOA, GPIO_AF10, GPIO9 | GPIO10| GPIO11 | GPIO12);
|
||||||
usbdev = usbd_init(&stm32f107_usb_driver,
|
dfu_init(&stm32f107_usb_driver);
|
||||||
&dev, &config, usb_strings, 4);
|
|
||||||
#else
|
#else
|
||||||
usbdev = usbd_init(&stm32f103_usb_driver,
|
dfu_init(&stm32f103_usb_driver);
|
||||||
&dev, &config, usb_strings, 4);
|
|
||||||
#endif
|
#endif
|
||||||
usbd_set_control_buffer_size(usbdev, sizeof(usbd_control_buffer));
|
|
||||||
usbd_register_control_callback(usbdev,
|
|
||||||
USB_REQ_TYPE_CLASS | USB_REQ_TYPE_INTERFACE,
|
|
||||||
USB_REQ_TYPE_TYPE | USB_REQ_TYPE_RECIPIENT,
|
|
||||||
usbdfu_control_request);
|
|
||||||
|
|
||||||
#if defined(BLACKMAGIC)
|
#if defined(BLACKMAGIC)
|
||||||
gpio_set(GPIOA, GPIO8);
|
gpio_set(GPIOA, GPIO8);
|
||||||
|
@ -373,45 +202,9 @@ int main(void)
|
||||||
GPIO_CNF_OUTPUT_PUSHPULL, GPIO8);
|
GPIO_CNF_OUTPUT_PUSHPULL, GPIO8);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
while (1)
|
dfu_main();
|
||||||
usbd_poll(usbdev);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static char *get_dev_unique_id(char *s)
|
|
||||||
{
|
|
||||||
#if defined(STM32F4) || defined(STM32F2)
|
|
||||||
#define UNIQUE_SERIAL_R 0x1FFF7A10
|
|
||||||
#define FLASH_SIZE_R 0x1fff7A22
|
|
||||||
#elif defined(STM32F3)
|
|
||||||
#define UNIQUE_SERIAL_R 0x1FFFF7AC
|
|
||||||
#define FLASH_SIZE_R 0x1fff77cc
|
|
||||||
#elif defined(STM32L1)
|
|
||||||
#define UNIQUE_SERIAL_R 0x1ff80050
|
|
||||||
#define FLASH_SIZE_R 0x1FF8004C
|
|
||||||
#else
|
|
||||||
#define UNIQUE_SERIAL_R 0x1FFFF7E8;
|
|
||||||
#define FLASH_SIZE_R 0x1ffff7e0
|
|
||||||
#endif
|
|
||||||
volatile uint32_t *unique_id_p = (volatile uint32_t *)UNIQUE_SERIAL_R;
|
|
||||||
uint32_t unique_id = *unique_id_p +
|
|
||||||
*(unique_id_p + 1) +
|
|
||||||
*(unique_id_p + 2);
|
|
||||||
int i;
|
|
||||||
|
|
||||||
/* Calculated the upper flash limit from the exported data
|
|
||||||
in theparameter block*/
|
|
||||||
max_address = (*(u32 *) FLASH_SIZE_R) <<10;
|
|
||||||
/* Fetch serial number from chip's unique ID */
|
|
||||||
for(i = 0; i < 8; i++) {
|
|
||||||
s[7-i] = ((unique_id >> (4*i)) & 0xF) + '0';
|
|
||||||
}
|
|
||||||
for(i = 0; i < 8; i++)
|
|
||||||
if(s[i] > '9')
|
|
||||||
s[i] += 'A' - '9' - 1;
|
|
||||||
s[8] = 0;
|
|
||||||
|
|
||||||
return s;
|
|
||||||
}
|
|
||||||
|
|
||||||
void sys_tick_handler()
|
void sys_tick_handler()
|
||||||
{
|
{
|
||||||
|
|
|
@ -0,0 +1,41 @@
|
||||||
|
/*
|
||||||
|
* This file is part of the Black Magic Debug project.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2013 Gareth McMullin <gareth@blacksphere.co.nz>
|
||||||
|
*
|
||||||
|
* 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 <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <libopencm3/usb/usbd.h>
|
||||||
|
|
||||||
|
#ifdef STM32F4
|
||||||
|
# define APP_ADDRESS 0x08010000
|
||||||
|
#else
|
||||||
|
# define APP_ADDRESS 0x08002000
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/* dfucore.c - DFU core, common to libopencm3 platforms. */
|
||||||
|
void dfu_init(const usbd_driver *driver);
|
||||||
|
void dfu_main(void);
|
||||||
|
|
||||||
|
/* Device specific functions */
|
||||||
|
void dfu_check_and_do_sector_erase(uint32_t sector);
|
||||||
|
void dfu_flash_program_buffer(uint32_t baseaddr, void *buf, int len);
|
||||||
|
uint32_t dfu_poll_timeout(uint8_t cmd, uint32_t addr, uint16_t blocknum);
|
||||||
|
void dfu_protect_enable(void);
|
||||||
|
void dfu_jump_app_if_valid(void);
|
||||||
|
|
||||||
|
/* Platform specific function */
|
||||||
|
void dfu_detach(void);
|
||||||
|
|
|
@ -22,7 +22,7 @@ all: blackmagic.bin blackmagic_dfu.bin blackmagic_dfu.hex
|
||||||
blackmagic.bin: blackmagic
|
blackmagic.bin: blackmagic
|
||||||
$(OBJCOPY) -O binary $^ $@
|
$(OBJCOPY) -O binary $^ $@
|
||||||
|
|
||||||
blackmagic_dfu: usbdfu.o
|
blackmagic_dfu: usbdfu.o dfucore.o dfu_f1.o
|
||||||
$(CC) $^ -o $@ $(LDFLAGS_BOOT)
|
$(CC) $^ -o $@ $(LDFLAGS_BOOT)
|
||||||
|
|
||||||
blackmagic_dfu.bin: blackmagic_dfu
|
blackmagic_dfu.bin: blackmagic_dfu
|
||||||
|
|
|
@ -40,7 +40,9 @@ extern usbd_device *usbdev;
|
||||||
#define CDCACM_GDB_ENDPOINT 1
|
#define CDCACM_GDB_ENDPOINT 1
|
||||||
#define CDCACM_UART_ENDPOINT 3
|
#define CDCACM_UART_ENDPOINT 3
|
||||||
#define BOARD_IDENT "Black Magic Probe (STM32_CAN), (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
#define BOARD_IDENT "Black Magic Probe (STM32_CAN), (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
||||||
|
#define BOARD_IDENT_DFU "Black Magic (Upgrade) for STM32_CAN, (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
||||||
#define DFU_IDENT "Black Magic Firmware Upgrade (STM32_CAN)"
|
#define DFU_IDENT "Black Magic Firmware Upgrade (STM32_CAN)"
|
||||||
|
#define DFU_IFACE_STRING "@Internal Flash /0x08000000/4*002Ka,124*002Kg"
|
||||||
|
|
||||||
/* Important pin mappings for STM32 implementation:
|
/* Important pin mappings for STM32 implementation:
|
||||||
*
|
*
|
||||||
|
|
|
@ -23,7 +23,7 @@ all: blackmagic.bin blackmagic_dfu.bin blackmagic_dfu.hex
|
||||||
blackmagic.bin: blackmagic
|
blackmagic.bin: blackmagic
|
||||||
$(OBJCOPY) -O binary $^ $@
|
$(OBJCOPY) -O binary $^ $@
|
||||||
|
|
||||||
blackmagic_dfu: usbdfu.o
|
blackmagic_dfu: usbdfu.o dfucore.o dfu_f4.o
|
||||||
$(CC) $^ -o $@ $(LDFLAGS_BOOT)
|
$(CC) $^ -o $@ $(LDFLAGS_BOOT)
|
||||||
|
|
||||||
blackmagic_dfu.bin: blackmagic_dfu
|
blackmagic_dfu.bin: blackmagic_dfu
|
||||||
|
|
|
@ -36,7 +36,9 @@
|
||||||
#define CDCACM_PACKET_SIZE 64
|
#define CDCACM_PACKET_SIZE 64
|
||||||
#define PLATFORM_HAS_TRACESWO
|
#define PLATFORM_HAS_TRACESWO
|
||||||
#define BOARD_IDENT "Black Magic Probe (USPS_F407), (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
#define BOARD_IDENT "Black Magic Probe (USPS_F407), (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
||||||
|
#define BOARD_IDENT_DFU "Black Magic (Upgrade) for USPS_F407, (Firmware 1.5" VERSION_SUFFIX ", build " BUILDDATE ")"
|
||||||
#define DFU_IDENT "Black Magic Firmware Upgrade (USPS_F407)"
|
#define DFU_IDENT "Black Magic Firmware Upgrade (USPS_F407)"
|
||||||
|
#define IFACE_STRING "@Internal Flash /0x08000000/1*016Ka,3*016Kg,1*064Kg,7*128Kg"
|
||||||
|
|
||||||
extern usbd_device *usbdev;
|
extern usbd_device *usbdev;
|
||||||
#define CDCACM_GDB_ENDPOINT 1
|
#define CDCACM_GDB_ENDPOINT 1
|
||||||
|
|
Loading…
Reference in New Issue