[i] Использование DFU-загрузчика для микроконтроллеров К1986ВЕ92FI, К1986ВЕ92F1I, K1986ВЕ92QI, К1986ВЕ92У(1)

ID статьи: 69528
Дата последнего изменения: 29.10.2026 14:11:36
DFU-загрузчик позволяет обновлять прошивку микроконтроллера по USB без JTAG/SWD-программатора. Загрузчик работает в соответствии со спецификацией USB Device Firmware Upgrade Specification, Revision 1.1.

Загрузчик размещается в начале основной FLASH-памяти микроконтроллера и занимает две страницы по 4 кБ, то есть 8 кБ. Это необходимо учитывать при линковке основной (загружаемой) программы. Она должна начинаться с адреса 0x8002000 и занимать до 0x1E000 (122880) байт.

Содержание статьи:
1. Что такое DFU?
2. Описание проекта
3. Механизм работы загрузчика
4. Настройка загрузчика
5. Настройка проекта основной программы
6. Подготовка к работе с DFU-загрузчиком
7. Работа с dfu-util


1. Что такое DFU?

DFU (Device Firmware Upgrade) – механизм обновления встроенного программного обеспечения устройств, поддерживающих USB. Он определяет порядок взаимодействия хоста и устройства при передаче новой версии прошивки и позволяет обновлять ее без подключения внешнего программатора.

Во время обновления устройство временно прекращает выполнять свои основные функции и переходит в режим программирования памяти. Например, устройство, которое в обычном режиме работает как измерительный прибор, на время обновления предоставляет хосту интерфейс для записи новой прошивки.

DFU определяет набор USB-дескрипторов, управляющих запросов и состояний, необходимых для обновления. Хост передает образ прошивки блоками, а устройство записывает их в энергонезависимую память. Упрощенная схема сеанса DFU представлена на рисунке 1.

Для реализации стороны хоста можно использовать утилиту dfu-util, она позволяет обнаруживать подключенные устройства, передавать в них образы прошивок, а также считывать содержимое памяти.


Рисунок 1 – Упрощенная схема сеанса DFU

2. Описание проекта

Структура проекта:
Загрузчик размещается в начале основной FLASH-памяти и занимает две страницы. Для микроконтроллера К1986ВЕ92x размер страницы составляет 4 кБ, поэтому под загрузчик отводится 8 кБ. Основная программа должна начинаться с 0x08002000 и занимать не более 0x1E000 байт (120 кБ). Ограничений на использование RAM загрузчик не накладывает.

При расширении функциональности размер загрузчика может увеличиться. В этом случае под него необходимо выделить целое число страниц FLASH-памяти, достаточное для размещения образа, а затем скорректировать начальный адрес и доступный размер области основной программы.

Архив с загрузчиком содержит исходные файлы и три проекта для следующих сред разработки:

Таблица 1 – Проекты для различных сред разработки
Среда разработки Каталог проекта 
 Keil µVision 5  MDR32FxQI_dfu_uv5/
 IAR Embedded Workbench for Arm  MDR32FxQI_dfu_IAR/
 Eclipse Embedded CDT  MDR32FxQI_dfu_eclipse/

Перед открытием проекта необходимо распаковать архив с сохранением структуры каталогов. Папки source/ и library/ используются проектами совместно, поэтому переносить только каталог выбранной среды разработки отдельно от остальных файлов не следует.

3. Механизм работы загрузчика

При запуске загрузчик переходит в режим обновления прошивки, если выполняется хотя бы одно из следующих условий:
  • в основной FLASH-памяти отсутствует программа (проверяется корректность указателя стека и вектора сброса);
  • на выводе DFU_BTN_PIN порта DFU_BTN_PORT, заданного в файле dfu_config.h (по умолчанию PB6), установлен логический уровень, соответствующий режиму работы загрузчика;
  • установлен программный флаг перехода в режим загрузчика (специальное значение в заранее выбранной ячейке SRAM или регистре BKP.
Механизм хранения и обработки флага зависит от особенностей конечного устройства, поэтому функция is_bootloader_flag_set в файле source/main.c реализована как заглушка. Для использования этого способа необходимо самостоятельно выбрать место хранения и значение флага, а также реализовать его проверку в загрузчике.

Если ни одно из перечисленных выше условий не выполнено, начинает выполняться основная программа.

Для индикации состояния загрузчика используется светодиод (по умолчанию PB7), который задается в файле source/dfu_config.h. После конфигурирования устройства хостом светодиод горит постоянно, сигнализируя о готовности загрузчика к работе. Если питание подано, но устройство не сконфигурировано, светодиод мигает с частотой 1 Гц.

Опрос вывода входа в режим загрузчика и светодиодная индикация необязательны. Их можно изменить или удалить из проекта.

4. Настройка загрузчика

Параметры загрузчика задаются в файле source/dfu_config.h и представлены в таблице 2. Изменения вступают в силу после повторной сборки проекта.

Таблица 2 – Параметры загрузчика
 Параметр  Назначение
 BOOTLOADER_VERSION_MAJOR  Старшая часть номера версии загрузчика
 BOOTLOADER_VERSION_MINOR  Младшая часть номера версии загрузчика
 DFU_VID  Идентификатор производителя
 DFU_PID  Идентификатор устройства
 FINISH_BY_METHOD

0 Загрузчик переходит из состояния DFU_STATE_MANIFEST_SYNC в DFU_STATE_IDLE и ожидает следующих команд. Утилита dfu-util инициирует сброс USB только при наличии ключа -R
1 Загрузчик переходит из состояния DFU_STATE_MANIFEST_SYNC в DFU_STATE_MANIFEST_WAIT_RESET. Утилита dfu-util обнаруживает это состояние и инициирует сброс USB независимо от наличия ключа -R

 CAN_WRITE_FW  
0  Запись запрещена
1  Запись разрешена

 CAN_READ_FW
0  Чтение запрещено 
1  Чтение разрешено

 DFU_BTN_PORT
 DFU_BTN_PIN
 DFU_BTN_PCLK
Вывод, опрашиваемый для входа в режим DFU
 DFU_BTN_STATE_FOR_DFU Логический уровень на выводе, при котором активируется режим DFU
 DFU_LED_PORT
 DFU_LED_PIN
 DFU_LED_PCLK
Вывод, к которому подключен светодиод
 DFU_LED_ACTIVE_STATE Логический уровень включения светодиода
 DFU_SUPPORT_FOR_INFORMATIONAL_EEPROM
 0 Доступна только основная память (Internal FLASH)
 1 Доступна основная (Internal FLASH) и информационная память (Internal EEPROM)

 BOOTLOADER_SIZE Размер области FLASH-памяти, выделенной под загрузчик

При объявлении SKIP_EEPROM_CALIB_INFO_PROTECTION в source/MDR32FxQI_config.h отключается реализованная в SPL программная защита сектора A информационной памяти от стирания. В результате становится доступна перезапись всей информационной памяти.
Сохранность заводских настроек в этом случае должен обеспечить пользователь.

Стирание FLASH-памяти выполняется постранично, поэтому запись даже одного байта в страницу, содержащую калибровочные значения, приведет к их удалению при стирании этой страницы. Перед записью необходимо считать заводские калибровочные значения в файл, объединить их с данными, которые нужно записать в информационную память.

Готовый бинарный файл загрузчика собран со следующими параметрами:
source/dfu_config.h
#define BOOTLOADER_VERSION_MAJOR                1
#define BOOTLOADER_VERSION_MINOR                0
#define DFU_VID                                 0x1209
#define DFU_PID                                 0x2E05
#define FINISH_BY_IDLE                          0
#define FINISH_BY_BUS_RESET                     1
#define FINISH_BY_METHOD                        FINISH_BY_IDLE
#define CAN_WRITE_FW                            1
#define CAN_READ_FW                             1
#define DFU_BTN_PORT                            MDR_PORTB
#define DFU_BTN_PIN                             PORT_Pin_6
#define DFU_BTN_STATE_FOR_DFU                   0
#define DFU_BTN_PCLK                            RST_CLK_PCLK_PORTB
#define DFU_LED_PORT                            MDR_PORTB
#define DFU_LED_PIN                             PORT_Pin_7
#define DFU_LED_ACTIVE_STATE                    1
#define DFU_LED_PCLK                            RST_CLK_PCLK_PORTB
#define DFU_SUPPORT_FOR_INFORMATIONAL_EEPROM    1
#define EEPROM_PAGE_SIZE 0x00001000 #define BOOTLOADER_SIZE (2 * EEPROM_PAGE_SIZE)
source/MDR32FxQI_config.h
//#define SKIP_EEPROM_CALIB_INFO_PROTECTION

5. Настройка проекта основной программы

Для корректной работы программы, загружаемой через DFU-загрузчик необходимо настроить проект так, чтобы код размещался в области памяти, не пересекающейся с загрузчиком.
Если настройки расположения загрузчика в памяти не менялись, то основная (загружаемая) программа должна размещаться следующим образом:
Настройка проекта в Keil uVision 5:
1. Необходимо открыть свойства проекта.
2. Перейти во вкладку «Target».
3. В области IROM1 указать следующие значения (рисунок 2):
  • Start – 0x8002000
  • Size – 0x1E000 
Область IRAM1 изменять не нужно.


Рисунок 2 – Свойства проекта, вкладка «Target»

4. Во вкладке «Linker» необходимо установить галочку «Use Memory Layout from Target Dialog» (рисунок 3), чтобы компоновщик использовал параметры, заданные во вкладке «Target».


Рисунок 3 – Свойства проекта, вкладка «Linker»

5. Для загрузки прошивки через DFU-загрузчик, она должна быть в бинарном формате. Файл HEX или ELF необходимо предварительно преобразовать в BIN. Чтобы это происходило автоматически после каждой сборки проекта, надо открыть вкладку «User», в разделе «After Build/Rebuild» установить галочку «Run #1»  и напротив нее в поле «User Command» ввести команду fromelf.exe --bin --output="@L.bin" "!L" (рисунок 4).


Рисунок 4 – Свойства проекта, вкладка «User»

6. Далее необходимо собрать проект. После сборки в папке проекта будет создан файл прошивки в формате BIN.
Настройка проекта в Eclipse IDE for Embedded C/C++ Developers:
Создание и базовая настройка проекта описаны в статье Установка IDE Eclipse.

1. Необходимо открыть используемый проектом скрипт компоновщика.
Путь к нему указывается в настройках проекта C/C++ Build -> Settings -> GNU Arm Cross C Linker -> General.
В разделе MEMORY надо задать для области FLASH следующие параметры:
  • ORIGIN – 0x08002000;
  • LENGTH – 0x1E000.
FLASH (rx) : ORIGIN = 0x08002000, LENGTH = 0x1E000

2. Для автоматического создания BIN-файла после сборки проекта требуется открыть настройки проекта «C/C++ Build -> Settings -> Build Steps» и в «Post-build steps» добавить команду arm-none-eabi-objcopy -O binary "${BuildArtifactFileName}" "${BuildArtifactFileBaseName}.bin" (рисунок 2).

Рисунок 2 – Настройка автоматического создания BIN-файла

3. После применения настроек требуется выбрать в меню «Project» и нажать «Clean».
В открывшемся окне надо выбрать проект и установить галочки, как на рисунке 3.

Рисунок 3 – Очистка результатов предыдущей сборки проекта и повторная сборка

После нажатия на кнопку «Clean» начнется очистка и новая сборка проекта. После окончания сборки в папке со сборкой появится файл прошивки с расширением .bin.
Настройка проекта в IAR Embedded Workbench for Arm:
Создание и базовая настройка проекта описаны в статье Установка IDE IAR. Создание нового проекта.

1. Необходимо открыть настройки проекта, выбрать раздел «Linker» и открыть вкладку «Config». Затем установить галочку «Override default» и нажать кнопку «Edit» (рисунок 2).

Рисунок 2 – Настройка конфигурации компоновщика

2. В открывшемся окне во вкладке Vector Table в поле .intvec start необходимо указать адрес 0x08002000 (рисунок 3).

Рисунок 3 – Настройка начального адреса таблицы векторов

Затем перейти во вкладку «Memory Regions» и задать для области ROM следующие значения (рисунок 4):
  • Start – 0x08002000;
  • End – (0x08000000+0x0001E000-1).

Рисунок 4 – Настройка области памяти основной программы

Параметры области RAM изменять необязательно. После внесения изменений необходимо нажать «Save» и сохранить файл конфигурации компоновщика.
3. Для автоматического создания файла прошивки в формате BIN необходимо выбрать раздел «Output Converter», установить галочку «Generate additional output» и в выпадающем списке «Output format» выбрать «Raw binary» (рисунок 5).

Рисунок 5 – Настройка автоматического создания бинарного файла прошивки

4. После сохранения настроек необходимо выполнить повторную сборку проекта (перед этим желательно очистить результаты предыдущей сборки). Файл прошивки с расширением .bin будет создан в подкаталоге Exe выбранной конфигурации сборки, например Debug/Exe.

6. Подготовка к работе с DFU-загрузчиком


При подключении устройства в режиме загрузчика к компьютеру под управлением Windows ему автоматически должен назначиться стандартный драйвер WinUSB. Устройство должно появиться в диспетчере устройств (рисунок 6).

Рисунок 6 – Диспетчер устройств

При необходимости драйвер WinUSB можно заменить на libusbK с помощью программы Zadig. Ее можно скачать с сайта https://zadig.akeo.ie/. Программу нужно запустить с правами администратора. В меню «Options» требуется выбрать пункт «List All Devices», после чего отобразятся все устройства, подключенные к ПК. В списке устройств необходимо выбрать Milandr <название_микроконтроллера> in DFU mode, далее выбрать драйвер libusbK и нажать кнопку «Replace Driver» (рисунок 7). По завершении установки драйвера программа отобразит окно с соответствующим сообщением.


Рисунок 7 – Смена драйвера в Zadig
При выборе драйвера следует учитывать, что WinUSB не позволяет инициировать программный сброс на шине USB. Если после обновления прошивки требуется сброс, следует использовать драйвер libusbK.

Для чтения и программирования памяти можно использовать утилиту dfu-util.

7. Работа с dfu-util

Обнаружение устройств в режиме DFU

Для вывода списка подключенных к компьютеру устройств в режиме DFU используется команда:
dfu-util -l
Пример вывода:
dfu-util 0.11
Copyright 2005-2009 Weston Schmidt, Harald Welte and OpenMoko Inc. Copyright 2010-2021 Tormod Volden and Stefan Schmidt This program is Free Software and has ABSOLUTELY NO WARRANTY Please report bugs to http://sourceforge.net/p/dfu-util/tickets/
Found DFU: [1209:2e05] ver=0100, devnum=9, cfg=1, intf=0, path="1-1", alt=1, name="Internal EEPROM", serial="00000001" Found DFU: [1209:2e05] ver=0100, devnum=9, cfg=1, intf=0, path="1-1", alt=0, name="Internal FLASH", serial="00000001"
При DFU_SUPPORT_FOR_INFORMATIONAL_EEPROM = 1 в выводе dfu-util отображаются два DFU-интерфейса, они относятся к одному устройству и предоставляют доступ к определенной области памяти:

Программирование FLASH-памяти:

Для записи файла example.bin в основную память микроконтроллера, надо выполнить команду:
dfu-util -a 0 -D example.bin
Параметр -a 0 выбирает интерфейс DFU по его alt-номеру, в данному случае используется Internal FLASH.

Пример вывода:
dfu-util 0.11

Copyright 2005-2009 Weston Schmidt, Harald Welte and OpenMoko Inc.
Copyright 2010-2021 Tormod Volden and Stefan Schmidt
This program is Free Software and has ABSOLUTELY NO WARRANTY
Please report bugs to http://sourceforge.net/p/dfu-util/tickets/

Warning: Invalid DFU suffix signature
A valid DFU suffix will be required in a future dfu-util release
Opening DFU capable USB device...
Device ID 1209:2e05
Device DFU version 0110
Claiming USB DFU Interface...
Setting Alternate Interface #0 ...
Determining device status...
DFU state(2) = dfuIDLE, status(0) = No error condition is present
DFU mode device DFU version 0110
Device returned transfer size 1024
Copying data from PC to DFU device
Download        [=========================] 100%       122880 bytes
Download done.
DFU state(6) = dfuMANIFEST-SYNC, status(0) = No error condition is present
DFU state(6) = dfuMANIFEST-SYNC, status(0) = No error condition is present
DFU state(2) = dfuIDLE, status(0) = No error condition is present
Done!

Чтение FLASH-памяти:

Команда:
dfu-util -a 0 -U flash.bin
Вывод:
dfu-util 0.11

Copyright 2005-2009 Weston Schmidt, Harald Welte and OpenMoko Inc.
Copyright 2010-2021 Tormod Volden and Stefan Schmidt
This program is Free Software and has ABSOLUTELY NO WARRANTY
Please report bugs to http://sourceforge.net/p/dfu-util/tickets/

Opening DFU capable USB device...
Device ID 1209:2e05
Device DFU version 0110
Claiming USB DFU Interface...
Setting Alternate Interface #0 ...
Determining device status...
DFU state(2) = dfuIDLE, status(0) = No error condition is present
DFU mode device DFU version 0110
Device returned transfer size 1024
Copying data from DFU device to PC
Upload  [=========================] 100%       122880 bytes
Upload done.
Received a total of 122880 bytes


Контактная информация

Сайт:https://support.milandr.ru
E-mail:support@milandr.ru
Телефон: +7 495 221-13-55