feat(protocan-boot): Добавь порты MCU и сервисы загрузки
Обеспечь единый процесс обновления для STM32F103/F407/G474 и TMS320F2812/F28335: discovery, служебные ответы, BUSY, тайм-аут сессии и подтверждение приложения. Добавь самостоятельные проекты CCS, аппаратные хранилища и Python-клиент. Совместимость: структуры конфигурации и порта расширены, поэтому потребители должны пересобраться и обнулить новые поля. Для C28x callbacks используют pcan_boot_byte_t; периодический pcan_boot_poll обслуживает discovery и настроенный тайм-аут.
This commit is contained in:
@@ -0,0 +1,109 @@
|
||||
# STM32: общий слой ProtoCAN Boot v1
|
||||
|
||||
Порты [F103C8](../stm32f103/README.md), [F407VE](../stm32f407/README.md) и
|
||||
[G474VE](../stm32g474/README.md) подключают bxCAN/FDCAN и Flash к текущему `pcan_boot`.
|
||||
F103/F407 предоставляют как лёгкий CMSIS boot main для существующих проектов,
|
||||
так и независимый HAL-порт. G474 использует HAL FDCAN/Flash.
|
||||
`pcan_boot_stm32.inc` включается семейным `.c`; отдельно его компилировать не надо.
|
||||
Сохраните рядом каталоги `stm32-common` и нужного семейства.
|
||||
|
||||
Reusable `pcan_boot_stm32*.c` не содержит `main` или startup. Готовые `boot_main.c`
|
||||
и вход из приложения находятся в семейных каталогах. Для F103/F407 общая
|
||||
CMSIS-реализация транспорта, callbacks и безопасного handoff — `boot_native.inc`;
|
||||
G474 также содержит `boot_startup.c` для исходных Keil/GCC-сборок.
|
||||
Тактирование платы, linker и привязка USB/CAN-приложения остаются в проектах.
|
||||
|
||||
KONOR, climate и CANdle G474 уже подключены через свои submodule: локальные
|
||||
boot main/control заменены include-обёртками, состав Keil/CMake обновлён.
|
||||
UART использует общий `rs485-boot` с сохранением SETGUI v1 wire-протокола.
|
||||
[Схема подключённых проектов и проверки сборок](../../projects/STM32.md).
|
||||
|
||||
## Подключение reusable HAL-портов F103/F407
|
||||
|
||||
1. Добавьте в сборку `src/pcan_boot.c` и семейный `pcan_boot_stm32f103.c`
|
||||
либо `pcan_boot_stm32f407.c`; в include paths — `include`, каталог порта,
|
||||
CMSIS, HAL и каталог вашего `stm32f1xx_hal_conf.h` / `stm32f4xx_hal_conf.h`.
|
||||
2. В HAL включите CAN, FLASH, RCC, GPIO и CORTEX. Выполните `HAL_Init`, настройте
|
||||
тактирование, SysTick и GPIO, вызовите `HAL_CAN_Init` для CAN1. Настройка скорости
|
||||
шины принадлежит проекту; исходные устройства используют 500 кбит/с.
|
||||
3. Выделите CAN1, FIFO0 и банки фильтров 0/1 загрузчику. Перед вызовом init CAN
|
||||
должен находиться в состоянии READY, без чужих активных фильтров. Init настраивает
|
||||
адресный фильтр и broadcast discovery, затем вызывает `HAL_CAN_Start`.
|
||||
Оба приоритета ProtoCAN разрешены, standard и remote кадры отвергаются.
|
||||
4. Не включайте CAN TX/RX IRQ для этого handle и не отправляйте через него кадры
|
||||
из других контекстов: порт использует опрос и сам читает TXOK до reset.
|
||||
5. Вызывайте семейный `poll` из основного цикла только после успешного init.
|
||||
Стирание Flash выполняется синхронно; вызов из IRQ не допускается.
|
||||
6. Linker приложения, VTOR и переход после reset должны соответствовать карте
|
||||
выбранного профиля. Изменение адресов требует отдельного согласования
|
||||
геометрии стирания, linker и host-клиента.
|
||||
|
||||
Пример для F103; `hcan` уже инициализирован проектом:
|
||||
|
||||
```c
|
||||
#include "pcan_boot_stm32f103.h" /* Подключает HAL-порт и текущий API общего автомата. */
|
||||
static pcan_boot_stm32_t updater; /* Сохраняет состояние между итерациями главного цикла. */
|
||||
static bool start_updater(CAN_HandleTypeDef *hcan) /* Вызывается после настройки CAN1, clock tree, GPIO и SysTick. */
|
||||
{ /* Настройка идентичности прибора не зависит от аппаратной геометрии Flash. */
|
||||
pcan_boot_config_t config = {0}; /* Не зависит от порядка полей расширяемого API. */
|
||||
config.device_type = 7U; /* Пример: тип 7 должен совпадать с выбранным адресом в клиенте прошивки. */
|
||||
config.device_id = 13U; /* Пример: номер 13 повторяет исходный адрес загрузчика KONOR. */
|
||||
config.ack_window = 16U; /* Подтверждает каждые 16 CAN-блоков по восемь байт. */
|
||||
config.session_timeout_ms = 30000U; /* Пример: 30 секунд без активности прерывают RAM-сессию. */
|
||||
return pcan_boot_stm32f103_init(&updater, hcan, &config); /* Настраивает single-slot геометрию, фильтры 0/1 и запускает CAN. */
|
||||
} /* После успеха основной цикл регулярно вызывает pcan_boot_stm32f103_poll(&updater). */
|
||||
```
|
||||
|
||||
Product/HW/FW в примере равны нулю; для изделия задайте их явно и согласуйте
|
||||
с manifest клиента. Порт сохраняет `ack_window` и `session_timeout_ms`, но сам
|
||||
задаёт `active_slot=0`, `slot_count=1`, `max_image_size` по физическому профилю.
|
||||
Конфигурацию `config` можно создавать на стеке; состояние `updater` и `hcan`
|
||||
должно существовать всё время работы загрузчика.
|
||||
|
||||
## Flash, подтверждения и reset
|
||||
|
||||
- Запись последовательная, блоки по восемь байт; неполная аппаратная единица
|
||||
допустима только в конце образа и дополняется `FF`. CRC учитывает полезную длину.
|
||||
- HAL-ошибки и readback каждого слова проверяются; после erase/program Flash
|
||||
снова блокируется, включая обработанные отказы. На F407 перед readback
|
||||
вызывается `FLASH_FlushCaches`, чтобы соседние записанные слова не читались
|
||||
из устаревшей строки Flash-кэша; состояние включения кэшей сохраняется HAL.
|
||||
- VERIFY перечитывает Flash, сравнивает её CRC и проверяет MSP/Thumb reset vector.
|
||||
Точка входа должна принадлежать фактическому образу, MSP — основной SRAM,
|
||||
с выравниванием восемь байт. CCM F407 в данном профиле для стека не используется.
|
||||
- COMMIT повторно проверяет образ и устанавливает признак в RAM.
|
||||
REBOOT разрешён только в состоянии COMMITTED. Ответ перед reset должен
|
||||
завершиться с TXOK; отсутствие mailbox, ошибка шины или тайм-аут 100 мс
|
||||
не вызывают reset. Для этого HAL tick должен работать при ожидании TX.
|
||||
- BUSY перед стиранием, между секторами F407 и после erase сохраняет активность
|
||||
сессии. На однобанковой Flash код не исполняется во время аппаратного стирания;
|
||||
непрерывные ответы в этот интервал не гарантируются. Настройте тайм-аут клиента
|
||||
больше максимального времени стирания одной аппаратной операции.
|
||||
|
||||
## Запуск приложения и потеря питания
|
||||
|
||||
Порт не меняет Option Bytes, защиту секторов и VDD; F407 требует 2,7..3,6 В
|
||||
для программирования x32. Переход из работающего приложения в загрузчик,
|
||||
backup/SRAM-флаг запроса, отключение периферии и безопасная замена MSP
|
||||
остаются в `main` и startup устройства.
|
||||
|
||||
`*_vectors_valid()` проверяет только векторы и диапазоны. После внешнего reset
|
||||
этого недостаточно для доказательства целостности образа: RAM-признак COMMIT
|
||||
потерян, а частично записанное приложение уже может иметь корректные векторы.
|
||||
Эти профили сохраняют исходную single-slot модель без постоянных метаданных,
|
||||
rollback, resume после питания и аутентификации. Для защищённого запуска
|
||||
проекту нужен отдельный постоянный manifest с полной проверкой образа.
|
||||
|
||||
## Проверка
|
||||
|
||||
`python tests/run_tests.py` из корня `protocan-boot` запускает три production-порта
|
||||
с моделью HAL и Flash, наряду с существующими проверками ядра и TI-портов.
|
||||
Можно также использовать обычные CMake/CTest: цели `test_stm32f103`,
|
||||
`test_stm32f407`, `test_stm32g474` работают на Windows и POSIX.
|
||||
|
||||
Проверяются все хвосты CAN-блока, полный ERASE/DATA/VERIFY/COMMIT/REBOOT,
|
||||
повреждение readback, отказы HAL/TX, фильтрация RX и сохранность памяти
|
||||
перед приложением и за верхней границей; для G474 проверяются оба DBANK-режима,
|
||||
переход между банками, запрет swap, ёмкость Flash и старое shifted-DLC HAL.
|
||||
Эти тесты не заменяют проверку
|
||||
на реальной плате с её linker, питанием, трансивером и SysTick.
|
||||
Reference in New Issue
Block a user