MyLibs 1.0
Расширенные библиотеки для STM32
Loading...
Searching...
No Matches
trace.h
Go to the documentation of this file.
1/**
2**************************************************************************
3* @file trace.h
4* @brief Заголочный файл для работы с трассировкой.
5**************************************************************************
6* @addtogroup TRACE Trace defines
7* @ingroup MYLIBS_DEFINES
8* @brief Дефайны для работы с трассировкой
9*************************************************************************/
10#ifndef __TRACE_H_
11#define __TRACE_H_
12#include "mylibs_defs.h"
13
14#include <string.h>
15/**
16 * @addtogroup TRACE_SERIAL Serial trace defines
17 * @ingroup TRACE
18 * @brief Дефайны для работы с serial трассировкой (SWO, RTT)
19 * @details Определяется дефайн @ref my_printf() и @ref log_printf() для работы с serial трассировкой:
20 - для RTT это будет вызов функции SEGGER_RTT_printf(), с подключением библиотеки SEGGER_RTT.h
21 - для SWO это будет просто printf()
22
23 Но библиотеку STDOUT надо подключить самостоятельно:
24
25 @verbatim
26 Manage Run-Time Environment -> Compiler -> I/O -> STDOUT
27 @endverbatim
28
29 Для SWO также надо включить трассировку:
30
31 @verbatim
32 Options For Target -> Debug -> Debugger Settings
33 @endverbatim
34
35 В вкладке Debug:
36 - Port = SW
37 В вкладке Trace:
38 - Указать Core Clock
39 - Выставить Trace Port = SWO
40 - ITM - выбрать нужный порт (для Keil нулевой порт)
41
42 - Если трассировка @ref SERIAL_TRACE_ENABLE отключена, то все дефайны определяются как 'ничего'
43 и на производительность кода не влияют
44
45 Если трассировка отключена, все макросы пустые и не влияют на производительность
46 * @{
47 *
48 * @def my_printf(...)
49 * @brief Универсальный макрос для вывода трассировки
50 * @details Варианты реализации:
51 * - RTT_TRACE_ENABLE `SEGGER_RTT_printf(0, ...)`
52 * - SWO_TRACE_ENABLE - `printf(...)`
53 * - NO_TRACE - пустой макрос
54 *
55 * @def log_printf(TAG, fmt, ...)
56 * @brief Макрос логирования с поддержкой уровней LOG_LEVEL
57 * @param TAG Тэг лога
58 * @param fmt, ... Форматируемая строка
59 * @details Варианты реализации:
60 * - LOG_LEVEL == 0 - логирование отключено (макрос пустой)
61 * - LOG_LEVEL == 1 - выводится время и TAG
62 * - LOG_LEVEL >= 2 - выводится время, TAG, имя файла и номер строки
63 */
64#ifdef SERIAL_TRACE_ENABLE
65
66 #if defined(RTT_TRACE_ENABLE)
67 #undef SWO_TRACE_ENABLE
68 #include "SEGGER_RTT.h"
69 #define my_printf(...) SEGGER_RTT_printf(0, __VA_ARGS__)
70 #elif defined(SWO_TRACE_ENABLE)
71 #undef RTT_TRACE_ENABLE
72 #define my_printf(...) printf(__VA_ARGS__)
73 #else // NO_TRACE
74 #define my_printf(...)
75 #warning No trace is selected. Serial debug wont work.
76 #endif // RTT_TRACE_ENABLE/SWO_TRACE_ENABLE/NO_TRACE
77#else //SERIAL_TRACE_ENABLE
78
79 #define my_printf(...)
80 #undef RTT_TRACE_ENABLE
81 #undef SWO_TRACE_ENABLE
82
83#endif //SERIAL_TRACE_ENABLE
84
85
86#ifndef LOG_LEVEL
87#define LOG_LEVEL 1 ///< @brief Уровень логирования (по умолчанию == 1)
88#endif
89
90#if LOG_LEVEL == 0 // лог отключен
91 #define \
92log_printf(TAG, fmt, ...)
93#elif LOG_LEVEL == 1 // только тэг
94 #define log_printf(TAG, fmt, ...) \
95my_printf("\n[%lu] [%s] " fmt, \
96(unsigned long)uwTick, TAG, ##__VA_ARGS__)
97#elif LOG_LEVEL >= 2 // всё
98 #define log_printf(TAG, fmt, ...) \
99my_printf("\n[%lu] [%s] (%s:%d) " fmt, \
100(unsigned long)uwTick, TAG, __FILE__, __LINE__, ##__VA_ARGS__)
101#endif
102
103/** TRACE_SERIAL
104 * @}
105 */
106
107/**
108 * @addtogroup TRACE_GPIO GPIO trace defines
109 * @ingroup TRACE
110 * @brief Дефайны для работы с GPIO трассировкой
111 * @details Определяется дефайны для работы с GPIO трассировкой:
112 - TRACE_GPIO_RESET() - для сброса ножки GPIO (через BSRR)
113 - TRACE_GPIO_SET() - для выставления ножки GPIO (через BSRR)
114
115 - Если трассировка @ref GPIO_TRACE_ENABLE отключена, то все дефайны определяются как 'ничего'
116 и на производительность кода не влияют
117 * @{
118 *
119 * @def TRACE_GPIO_RESET(_gpio_, _pin_)
120 * @brief Сбросить указанную ножку GPIO
121 * @param _gpio_ Указатель на структуру GPIO (напр. GPIOA)
122 * @param _pin_ Номер ножки (напр. GPIO_PIN_0)
123 * @details Варианты реализации:
124 * - GPIO_TRACE_ENABLE не определён - макрос пустой
125 * - GPIO_TRACE_ENABLE определён - устанавливает бит сброса через BSRR ((_pin_)<<16)
126 *
127 * @def TRACE_GPIO_SET(_gpio_, _pin_)
128 * @brief Установить указанную ножку GPIO
129 * @param _gpio_ Указатель на структуру GPIO (например GPIOA)
130 * @param _pin_ Номер ножки (напр. GPIO_PIN_0)
131 * @details Варианты реализации:
132 * - GPIO_TRACE_ENABLE не определён - макрос пустой
133 * - GPIO_TRACE_ENABLE определён - устанавливает бит установки через BSRR (_pin_)
134 */
135#ifndef GPIO_TRACE_ENABLE
136 #define TRACE_GPIO_SET(_gpio_,_pin_)
137 #define TRACE_GPIO_RESET(_gpio_,_pin_)
138#else
139 #define TRACE_GPIO_SET(_gpio_,_pin_) (_gpio_)->BSRR = (((_pin_)))
140 #define TRACE_GPIO_RESET(_gpio_,_pin_) (_gpio_)->BSRR = ((_pin_)<<16)
141#endif //GPIO_TRACE_ENABLE
142
143
144/** TRACE_GPIO
145 * @}
146 */
147
148
149
150#if defined(HAL_MODULE_ENABLED) && defined(RTT_TRACE_ENABLE)
151
152/**
153 * @addtogroup TRACE_RTT_FLASH Flash RTT Buffer
154 * @ingroup TRACE
155 * @brief Макросы и функции для сохранения/чтения RTT буфера в Flash
156 * @details Модуль позволяет сохранять данные RTT буфера во Flash и читать их обратно по тегам.
157 * Теги работают следующим образом:
158 * - Базовый тег (младший байт = 0): модуль сам выбирает первый свободный слот во Flash;
159 * новые записи получают автоинкрементированный младший байт тега (от 0x00 до 0xFF).
160 * - Конкретный тег (младший байт != 0): запись или чтение происходит строго с указанным тегом;
161 * если слот с таким тегом уже занят, запись не выполняется.
162 * - Автоинкремент позволяет хранить несколько последовательных записей в пределах одного базового тега,
163 * без необходимости вручную отслеживать адреса Flash или позиции буферов.
164 * @{
165 */
166
167
168/**
169 * @brief Структура RTT, которая будет положена в Flash
170 */
171typedef struct {
172 uint32_t tag; ///< Уникальный идентификатор буфера
173 uint32_t size; ///< Размер данных
174 char data[RTT_FLASH_BUFFER_SIZE]; ///< Буфер RTT
176
177/**
178 * @brief Подготовка Flash к записи
179 * @details Сбрасывает ошибки Flash и ожидает готовности перед записью
180 */
181__STATIC_FORCEINLINE void RTT_FlashPrepare(void)
182{
183 HAL_FLASH_Unlock();
184 __HAL_FLASH_CLEAR_FLAG(FLASH_FLAG_PGSERR | FLASH_FLAG_WRPERR | FLASH_FLAG_OPERR);
185 while (__HAL_FLASH_GET_FLAG(FLASH_FLAG_BSY)) {
186 __NOP();
187 }
188}
189
190/**
191 * @brief Сохраняет последние символы RTT-буфера в Flash по тегу
192 * @param tag Базовый или конкретный идентификатор буфера.
193 * @param tail_size Количество последних символов RTT для копирования
194 * @param buf_num Указатель на переменную в которую запишется номер буфера для конкретного тега
195 * @return >=0 — номер буфера (тег) для записи, <0 — ошибка (нет места, тег уже занят, ошибка записи в флеш)
196 *
197 * @details Автоматически копирует последние tail_size символов из RTT-буфера
198 * и записывает их во Flash.
199 * Тег может быть базовым или конкретным:
200 * - Если базовый (младший байт == 0) — будет выбран первый свободный слот с автоинкрементом.
201 * Автоинкремент формируется в пределах от 0x1 до 0xFF
202 * - Если конкретный (младший байт != 0) — запись выполняется только с этим тегом, иначе ошибка.
203 */
204__STATIC_FORCEINLINE int RTT_SaveToFlash(uint32_t tag, uint32_t tail_size)
205{
206 if (tag == 0xFFFFFFFF)
207 return -1; // Неверный тег
208
209 SEGGER_RTT_BUFFER_UP *up = &_SEGGER_RTT.aUp[0];
210 unsigned buf_size = up->SizeOfBuffer;
211 unsigned wr = up->WrOff;
212
213 // Ограничиваем по размеру буфера RTT и RTT_FLASH_BUFFER_SIZE
214 unsigned n = (tail_size > buf_size) ? buf_size : tail_size;
215 if (n > RTT_FLASH_BUFFER_SIZE)
217
218 uint32_t addr = RTT_FLASH_SECTOR_START;
219 RTT_FlashHeader_t *flash_hdr = NULL;
220 uint32_t base_tag = tag & 0xFFFFFF00;
221 uint32_t next_tag = (tag & 0xFF) == 0 ? tag + 1 : tag;
222
223 // Ищем первый свободный слот, параллельно автоинкрементируем тег
224 while ((addr + sizeof(RTT_FlashHeader_t)) <= RTT_FLASH_SECTOR_END)
225 {
226 flash_hdr = (RTT_FlashHeader_t *)addr;
227
228 if (flash_hdr->tag == 0xFFFFFFFF)
229 break; // Нашли свободное место
230
231
232 if((flash_hdr->tag & 0xFFFFFF00) == base_tag) // выбраный тег
233 {
234 if ((tag & 0xFF) == 0) // если он базовый - ищем последний
235 next_tag = flash_hdr->tag + 1; // автоинкремент
236 else
237 if(flash_hdr->tag == tag) // если он конкретный и уже существует - то ошибка
238 return -1; // конкретный тег уже занят
239 }
240
241
242 if(next_tag - tag > 0xFF)
243 return -1; // автоинкремент слишком большой
244
245 addr += sizeof(RTT_FlashHeader_t);
246 }
247
248 if ((addr + sizeof(RTT_FlashHeader_t)) > RTT_FLASH_SECTOR_END)
249 return -1; // Нет свободного места
250
251 // Копируем последние n символов из RTT
252 char temp[RTT_FLASH_BUFFER_SIZE];
253 unsigned valid_count = 0;
254
255 for (unsigned i = 0; i < n; i++)
256 {
257 unsigned idx = (wr + buf_size - n + i) % buf_size;
258 char c = up->pBuffer[idx];
259 if (c != 0)
260 temp[valid_count++] = c;
261 }
262
264
265 // Формируем структуру в RAM
266 RTT_FlashHeader_t flash_data;
267 flash_data.tag = next_tag;
268 flash_data.size = valid_count;
269 memcpy(flash_data.data, temp, valid_count);
270
271 // Записываем структуру во Flash (по 4 байта)
272 const uint32_t *p = (const uint32_t *)&flash_data;
273 for (unsigned i = 0; i < sizeof(RTT_FlashHeader_t) / 4; i++)
274 {
275 if(HAL_FLASH_Program(FLASH_TYPEPROGRAM_WORD, addr + i * 4, p[i]) != HAL_OK)
276 return -1;
277 }
278
279 HAL_FLASH_Lock();
280 __DSB();
281 __ISB();
282
283
284 return (int)(next_tag&0xFF);
285}
286
287
288/**
289 * @brief Читает последние символы RTT-буфера из Flash по тегу
290 * @param tag Базовый или конкретный идентификатор буфера.
291 * @param Buffer Буфер назначения для копирования данных
292 * @param tail_size Количество последних символов, которые нужно прочитать
293 * @param read_size Количество считанных символов
294 * @return >=0 — номер буфера (тег) для записи, <0 — ошибка (тег не найден или структура повреждена)
295 *
296 * @details Копирует последние tail_size символов из найденной записи Flash в Buffer.
297 * Тег может быть базовым или конкретным:
298 * - Если базовый (младший байт == 0) — будет прочитана последняя запись из группы.
299 * - Если конкретный (младший байт != 0) — прочитывается именно эта запись.
300 */
301__STATIC_FORCEINLINE int RTT_ReadFromFlash(uint32_t tag, char *Buffer, uint32_t tail_size, uint32_t *read_size)
302{
303 if (!Buffer || tail_size == 0)
304 return -1; // Неверные параметры
305
306 if (tag == 0xFFFFFFFF)
307 return -1; // Недопустимый тег
308
309 uint32_t addr = RTT_FLASH_SECTOR_START;
310 RTT_FlashHeader_t *flash_hdr = NULL;
311 RTT_FlashHeader_t *target_hdr = NULL;
312 uint32_t base_tag = tag & 0xFFFFFF00;
313
314 // Поиск записи по тегу
315 while ((addr + sizeof(RTT_FlashHeader_t)) <= RTT_FLASH_SECTOR_END)
316 {
317 flash_hdr = (RTT_FlashHeader_t *)addr;
318
319 if (flash_hdr->tag == 0xFFFFFFFF)
320 break; // Достигнут конец записанных структур
321
322 // выбраный тег
323 if((flash_hdr->tag & 0xFFFFFF00) == base_tag)
324 {
325 if ((tag & 0xFF) == 0) // если он базовый - ищем последний
326 target_hdr = flash_hdr; // сохраняем последний в группе
327 else
328 if(flash_hdr->tag == tag) // если он конкретный и найден - берем его
329 {
330 target_hdr = flash_hdr;
331 break; // конкретный тег найден
332 }
333 }
334
335 addr += sizeof(RTT_FlashHeader_t);
336 }
337
338 if (!target_hdr) return -1; // Тег не найден
339
340 // Проверка корректности размера
341 if (target_hdr->size > RTT_FLASH_BUFFER_SIZE)
342 return -1; // Повреждённая запись
343
344 // Определяем количество читаемых символов
345 uint32_t n = (tail_size > target_hdr->size) ? target_hdr->size : tail_size;
346 // Начальная позиция для чтения последних tail_size символов
347 uint32_t start = target_hdr->size - n;
348 // Копируем данные из Flash в RAM
349 memcpy(Buffer, &target_hdr->data[start], n);
350
351 if(read_size != NULL)
352 {
353 *read_size = n;
354 }
355
356 __DSB();
357 __ISB();
358
359 return (int)(target_hdr->tag & 0xFF);
360}
361
362/**
363 * @brief Стирание сектора Flash с RTT-буфером
364 */
365__STATIC_FORCEINLINE int RTT_EraseFlash(void)
366{
367 FLASH_EraseInitTypeDef eraseInit;
368 uint32_t pageError = 0;
369
371
372 eraseInit.TypeErase = FLASH_TYPEERASE_SECTORS;
373 eraseInit.Sector = RTT_FLASH_SECTOR;
374 eraseInit.NbSectors = 1;
375
376 if (HAL_FLASHEx_Erase(&eraseInit, &pageError) != HAL_OK)
377 {
378 return -1;
379 }
380 return 0;
381 HAL_FLASH_Lock();
382}
383
384/** TRACE_RTT_FLASH
385 * @}
386 */
387
388#else // HAL_MODULE_ENABLED && RTT_TRACE_ENABLE
389#define RTT_FlashPrepare()
390#define RTT_EraseFlash() 0
391#define RTT_SaveToFlash() 0
392#define RTT_ReadFromFlash() 0
393#endif // HAL_MODULE_ENABLED && RTT_TRACE_ENABLE
394
395
396
397
398/**
399 * @addtogroup TRACE_HARDFAULT Hardfault trace defines
400 * @ingroup TRACE
401 * @brief Модуль трассировки HardFault с возможностью сохранения RTT буфера во Flash
402 * @details
403 * Этот модуль позволяет сохранять контекст процессора и последние символы RTT буфера при возникновении HardFault.
404 *
405 * Механизм работы:
406 * - При срабатывании HardFault вызывается HF_HandleFault(), который:
407 * 1. Получает указатель на стек, где произошёл HardFault (MSP или PSP).
408 * 2. Выводит значения регистров R0-R3, R12, LR, PC, PSR и системных регистров SCB.
409 * 3. Формирует строку с регистрами и копирует последние символы RTT буфера.
410 * 4. Сохраняет данные во Flash с базовым тегом HF_RTT_TAG_BASE.
411 * - Для восстановления последнего HardFault используется HF_CheckRecovered(), который:
412 * 1. Читает запись во Flash по базовому тегу.
413 * 2. Выводит сохранённый RTT буфер и контекст регистров.
414 * 3. Опционально стирает Flash после восстановления.
415 @code
416 void Hardfault()
417 {
418 HF_HandleFault();
419 NVIC_SystemReset();
420 }
421
422 int main()
423 {
424 if(HF_CheckRecovered(0))
425 {
426 //set hardfault error
427 RTT_EraseFlash(); // erase rtt flash after message readed
428 }
429 }
430 @endcode
431 * @{
432 */
433#if defined(HAL_MODULE_ENABLED) && defined(HARDFAULT_SERIAL_TRACE)
434
435#ifndef HF_RTT_TAIL_SIZE
436#define HF_RTT_TAIL_SIZE RTT_FLASH_BUFFER_SIZE ///< Размер буфера RTT, который сохранится при Hardfault
437#endif
438
439/**
440 * @brief Контекст стек-фрейма процессора при HardFault
441 * @details Сохраняет регистры R0-R3, R12, LR, PC, PSR для последующего анализа.
442 */
443typedef struct {
444 uint32_t r0; ///< Регистр R0
445 uint32_t r1; ///< Регистр R1
446 uint32_t r2; ///< Регистр R2
447 uint32_t r3; ///< Регистр R3
448 uint32_t r12; ///< Регистр R12
449 uint32_t lr; ///< Link Register
450 uint32_t pc; ///< Program Counter
451 uint32_t psr; ///< Program Status Register
453
454/**
455 * @brief Проверка и вывод последнего HardFault-трейса из Flash
456 * @details
457 * Функция ищет последнюю запись HardFault по базовому тегу HF_RTT_TAG_BASE
458 * и выводит её содержимое в консоль. После успешного вывода Flash можно опционально очистить.
459 *
460 * @return int
461 * - 1 — данные HardFault найдены и выведены
462 * - 0 — данные отсутствуют или тег не найден
463 *
464 * @note Вызов рекомендуется при инициализации приложения для анализа предыдущего сбоя.
465 */
466__STATIC_FORCEINLINE int HF_CheckRecovered(int erase)
467{
468 char buffer[RTT_FLASH_BUFFER_SIZE];
469 uint32_t read_size = 0;
470 int n_hardfault = RTT_ReadFromFlash(HF_RTT_TAG_BASE, buffer, HF_RTT_TAIL_SIZE, &read_size);
471 if (n_hardfault > 0)
472 {
473 my_printf("\n--- Recovered HardFault RTT buffer #%u ---\n", n_hardfault);
474 for (int i = 0; i < read_size; i++)
475 {
476 char c = buffer[i];
477 if (c == 0 || c == (char)0xFF) break;
478 my_printf("%c", c);
479 }
480
481 if(erase)
483 my_printf("\n--------- HardFault Dump End ---------\n");
484 return 1;
485 }
486 return 0;
487}
488
489
490static HF_StackFrame_t *stack_frame;
491static uint32_t stack_dump[HF_STACK_DUMP_WORDS];
492static void *ret_adr[10] = {0};
493/**
494 * @brief Обработчик HardFault
495 * @details
496 * Вызывается из прерывания HardFault или в любом месте где понятно что ошибка критическая.
497 * Последовательно выполняет:
498 * 1. Определяет активный стек (MSP или PSP) на момент сбоя.
499 * 2. Сохраняет значения регистров R0-R3, R12, LR, PC, PSR.
500 * 3. Выводит системные регистры CFSR, HFSR, DFSR, AFSR, MMFAR, BFAR.
501 * 4. Формирует stack trace с 3 уровнями возврата.
502 * 5. Копирует последние символы RTT буфера.
503 * 6. Сохраняет все данные во Flash через RTT_SaveToFlash с базовым тегом HF_RTT_TAG_BASE.
504 *
505 * @note Функция защищена, так как вызывается в контексте сбоя — минимизирует использование вызовов HAL.
506 */
507__STATIC_FORCEINLINE void HF_HandleFault(void)
508{
509 // Получаем указатель на стек, где произошёл HardFault
510 __ASM volatile(
511 "TST lr, #4 \n"
512 "ITE EQ \n"
513 "MRSEQ %[ptr], MSP\n"
514 "MRSNE %[ptr], PSP\n"
515 : [ptr] "=r"(stack_frame)
516 );
517
518 my_printf("\n===== HardFault occurred! =====\n");
519 my_printf("R0 = 0x%08X\n", stack_frame->r0);
520 my_printf("R1 = 0x%08X\n", stack_frame->r1);
521 my_printf("R2 = 0x%08X\n", stack_frame->r2);
522 my_printf("R3 = 0x%08X\n", stack_frame->r3);
523 my_printf("R12 = 0x%08X\n", stack_frame->r12);
524 my_printf("LR = 0x%08X\n", stack_frame->lr);
525 my_printf("PC = 0x%08X\n", stack_frame->pc);
526 my_printf("PSR = 0x%08X\n", stack_frame->psr);
527
528 my_printf("CFSR = 0x%08X\n", SCB->CFSR);
529 my_printf("HFSR = 0x%08X\n", SCB->HFSR);
530 my_printf("DFSR = 0x%08X\n", SCB->DFSR);
531 my_printf("AFSR = 0x%08X\n", SCB->AFSR);
532 my_printf("MMFAR = 0x%08X\n", SCB->MMFAR);
533 my_printf("BFAR = 0x%08X\n", SCB->BFAR);
534
535 // --- Stack trace ---
536 my_printf("--- Stack trace ---\n");
537 ret_adr[0] = __builtin_return_address(0);
538 ret_adr[1] = __builtin_return_address(1);
539 ret_adr[2] = __builtin_return_address(2);
540
541 for (int i = 0; i < 3; i++) // развернуть n уровней
542 {
543 if(ret_adr[i])
544 my_printf(" #%d: 0x%08lX\r\n", i, ret_adr[i]); // -1 для Thumb
545 }
547}
548#else // HAL_MODULE_ENABLED && HARDFAULT_SERIAL_TRACE
549#define HF_CheckRecovered() 0
550#define HF_HandleFault()
551#endif // HAL_MODULE_ENABLED && HARDFAULT_SERIAL_TRACE
552/** TRACE_HARDFAULT
553 * @}
554 */
555
556
557
558#endif //__TRACE_H_
#define RTT_FLASH_SECTOR
Сектор FLASH куда положится RTT буфер
#define RTT_FLASH_BUFFER_SIZE
Размер буфера RTT в Flash.
#define RTT_FLASH_SECTOR_START
Начало сектора RTT_FLASH_SECTOR.
#define HF_STACK_DUMP_WORDS
Сколько слов стека будет проанализировано во время Hardfault.
#define HF_RTT_TAG_BASE
базовый тег для HardFault
#define HF_RTT_TAIL_SIZE
Размер буфера RTT, который сохранится при Hardfault.
#define RTT_FLASH_SECTOR_END
Конец сектора RTT_FLASH_SECTOR.
__STATIC_FORCEINLINE int HF_CheckRecovered(int erase)
Проверка и вывод последнего HardFault-трейса из Flash.
Definition trace.h:466
__STATIC_FORCEINLINE void HF_HandleFault(void)
Обработчик HardFault.
Definition trace.h:507
__STATIC_FORCEINLINE void RTT_FlashPrepare(void)
Подготовка Flash к записи
Definition trace.h:181
__STATIC_FORCEINLINE int RTT_ReadFromFlash(uint32_t tag, char *Buffer, uint32_t tail_size, uint32_t *read_size)
Читает последние символы RTT-буфера из Flash по тегу
Definition trace.h:301
__STATIC_FORCEINLINE int RTT_SaveToFlash(uint32_t tag, uint32_t tail_size)
Сохраняет последние символы RTT-буфера в Flash по тегу
Definition trace.h:204
__STATIC_FORCEINLINE int RTT_EraseFlash(void)
Стирание сектора Flash с RTT-буфером
Definition trace.h:365
#define my_printf(...)
Универсальный макрос для вывода трассировки
Definition trace.h:69
Заголочный файл для дефайнов библиотеки MyLibsGeneral.
Контекст стек-фрейма процессора при HardFault.
Definition trace.h:443
uint32_t pc
Program Counter.
Definition trace.h:450
uint32_t r1
Регистр R1.
Definition trace.h:445
uint32_t r0
Регистр R0.
Definition trace.h:444
uint32_t r3
Регистр R3.
Definition trace.h:447
uint32_t r2
Регистр R2.
Definition trace.h:446
uint32_t lr
Link Register.
Definition trace.h:449
uint32_t r12
Регистр R12.
Definition trace.h:448
uint32_t psr
Program Status Register.
Definition trace.h:451
Структура RTT, которая будет положена в Flash.
Definition trace.h:171
uint32_t tag
Уникальный идентификатор буфера
Definition trace.h:172
char data[1024]
Буфер RTT.
Definition trace.h:174
uint32_t size
Размер данных
Definition trace.h:173