winniethepooh 0 3 декабря, 2021 Опубликовано 3 декабря, 2021 · Жалоба Здравствуйте. В случае фатальной ошибки (в таске или в обработчике) отобразить стек задачи и регистры процессора в момент ошибки. Как такое можно реализовать? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
haker_fox 60 3 декабря, 2021 Опубликовано 3 декабря, 2021 · Жалоба 19 minutes ago, winniethepooh said: Как такое можно реализовать? Что Вы понимаете под фатальной ошибкой? Если HardFault, то это прерывание позволяет вычитать регистры процессора и указатели на стэк (MSP/PSP). О, кстати! А микроконтроллер или процессор какой у Вас? Я по умолчанию уже для Cortex'ов начанию рассказывать. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
winniethepooh 0 6 декабря, 2021 Опубликовано 6 декабря, 2021 · Жалоба On 12/3/2021 at 6:28 PM, haker_fox said: Что Вы понимаете под фатальной ошибкой? Если HardFault, то это прерывание позволяет вычитать регистры процессора и указатели на стэк (MSP/PSP). О, кстати! А микроконтроллер или процессор какой у Вас? Я по умолчанию уже для Cortex'ов начанию рассказывать. Да я использую Cortex M4. Можно ли в случае ошибки в приложении FreeRTOS отобразить стек задачи с ошибкой и значения регистров контроллера в момент ошибки? Можно ли получить значения регистров, если ошибка произошла во время обработки прерывания? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
haker_fox 60 6 декабря, 2021 Опубликовано 6 декабря, 2021 · Жалоба 10 minutes ago, winniethepooh said: отобразить стек задачи с ошибкой и значения регистров контроллера в момент ошибки? Да. Но к FreeRTOS не имеет никакого отношения) И зависит от ошибки. Например, если принудительно не включить эту опцию, то невыровненный доступ ошибкой считаться не будет на Cortex-M4. А на Cortex-M0 будет ошибкой всегда. 10 minutes ago, winniethepooh said: Можно ли получить значения регистров, если ошибка произошла во время обработки прерывания? Да. В обоих случаях читайте про HardFault. Напишите для этого прерывания обработчик, который выдаст Вам значения регистров процессора в момент возникновения ошибки. Можете дополнительно вывести содержимое стэка. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
AlanDrakes 1 6 декабря, 2021 Опубликовано 6 декабря, 2021 · Жалоба Нахожу очень много вариаций этого кода: https://community.arm.com/support-forums/f/embedded-forum/4749/error-hard-fault-handler Собственно, нужен сам обработчик, который выведет сообщения, например, в консоль в виде дампа части стэка (весь восстановить сложновато, но и это уже что-то), и остановит выполнение. Все используют printf(), или его аналоги. Собственно, код: Скрытый текст void BusFault_Handler(void) { __asm volatile ( " tst lr, #4 \n" " ite eq \n" " mrseq r0, msp \n" " mrsne r0, psp \n" " ldr r1, [r0, #24] \n" " ldr r2, handler2_address_const \n" " bx r2 \n" " handler2_address_const: .word BusFault_Handler_c \n" ); } void BusFault_Handler_c(unsigned int * hardfault_args) { unsigned int stacked_r0; unsigned int stacked_r1; unsigned int stacked_r2; unsigned int stacked_r3; unsigned int stacked_r12; unsigned int stacked_lr; unsigned int stacked_pc; unsigned int stacked_psr; stacked_r0 = ((unsigned long) hardfault_args[0]); stacked_r1 = ((unsigned long) hardfault_args[1]); stacked_r2 = ((unsigned long) hardfault_args[2]); stacked_r3 = ((unsigned long) hardfault_args[3]); stacked_r12 = ((unsigned long) hardfault_args[4]); stacked_lr = ((unsigned long) hardfault_args[5]); stacked_pc = ((unsigned long) hardfault_args[6]); stacked_psr = ((unsigned long) hardfault_args[7]); DumpText ("\r\n[Bus fault handler - all numbers in hex]\r\n"); DumpText ("R0 = "); DumpHexDWord(stacked_r0); DumpText ("\r\nR1 = "); DumpHexDWord(stacked_r1); DumpText ("\r\nR2 = "); DumpHexDWord(stacked_r2); DumpText ("\r\nR3 = "); DumpHexDWord(stacked_r3); DumpText ("\r\nR12 = "); DumpHexDWord(stacked_r12); DumpText ("\r\nLR [R14] (subroutine call return address) = "); DumpHexDWord(stacked_lr); DumpText ("\r\nPC [R15] (program counter) = "); DumpHexDWord(stacked_pc); DumpText ("\r\nPSR = "); DumpHexDWord(stacked_psr); DumpText ("\r\nBFAR = "); DumpHexDWord((*((volatile unsigned long *)(0xE000ED38)))); DumpText ("\r\nCFSR = "); DumpHexDWord((*((volatile unsigned long *)(0xE000ED28)))); DumpText ("\r\nHFSR = "); DumpHexDWord((*((volatile unsigned long *)(0xE000ED2C)))); DumpText ("\r\nDFSR = "); DumpHexDWord((*((volatile unsigned long *)(0xE000ED30)))); DumpText ("\r\nAFSR = "); DumpHexDWord((*((volatile unsigned long *)(0xE000ED3C)))); DumpText ("\r\nSCB_SHCSR = "); DumpHexDWord(SCB->SHCSR); DumpText("\r\n"); while (1); }; BusFault_Handler - может быть как сам BusFault, так и остальные обработчики. Он НЕ должен изменять значение стэка. Я переписал под минималистические функции DumpXXX, которые почти не обрабатывают данные. Текст - просто выводит строку, HexDWord - выводит 32 бита HEX-кодом. Это единственное моё изменение. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
winniethepooh 0 6 декабря, 2021 Опубликовано 6 декабря, 2021 (изменено) · Жалоба спасибо за быстрый ответ haker_fox и AlanDarkes. Насколько я понял принцип такой: -вызвать событие HardFault или BusFault и в обработчике получить значения стека и регистров? да и еще watchdog до того как отправит контроллер на перезагрузку способен выдать прерывание. Можно ли использовать прерывание watchdog'a для события HardFault и насколько действительны данные в регистрах и стеке задачи в этом случае? Изменено 6 декабря, 2021 пользователем winniethepooh Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
haker_fox 60 6 декабря, 2021 Опубликовано 6 декабря, 2021 · Жалоба 18 minutes ago, winniethepooh said: -вызвать событие HardFault или BusFault и в обработчике получить значения стека и регистров? Дарагой, ну ты книгу-то уже почитай))) У того же Джозефа Ю. всё хорошо про этот "фолт" описано. Ничего вызывать не надо. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
winniethepooh 0 6 декабря, 2021 Опубликовано 6 декабря, 2021 (изменено) · Жалоба 11 minutes ago, haker_fox said: Дарагой, ну ты книгу-то уже почитай))) У того же Джозефа Ю. всё хорошо про этот "фолт" описано. Ничего вызывать не надо. Простите за малую осведомленность, у нас Джозефе пока никто не слышал.. Изменено 6 декабря, 2021 пользователем winniethepooh Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
winniethepooh 0 6 декабря, 2021 Опубликовано 6 декабря, 2021 · Жалоба нужно наверное пояснить что хотелось бы в итоге получить. задачи выполняют разные функции и если функция возвращает не успех, то после этой функции, отобразить содержимое регистров и стек, оставить задачу в бесконечном цикле. затем задача контролирующая watchdog не получает уведомления от задачи в бесконечном цикле и не препятствует watchdog'y в перезагрузке контроллера. Фактически меня интересует рабочий вариант контроля задач и отображения состояния стека задачи и регистров. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться