реклама на сайте
подробности

 
 
> Nested interrupts and Hard Fault, Происходит hard fault если есть вложенные прерывания
xelax
сообщение Jun 21 2016, 13:08
Сообщение #1


Местный
***

Группа: Свой
Сообщений: 370
Регистрация: 7-11-06
Пользователь №: 22 035



Исходные данные.
Код для cortex-m4 (nrf52), язык С, компилятор Keil.

Ситуация следующая. В принципе все ок и работает. Работаем в основном с GCC, но по условиям ТЗ код должен собираться и работать также на IAR и Keil, так что периодически билдим и запускаем код на них.
GCC и IAR работают без проблем. Keil падает в hard fault в рандомном месте. Первые подозрения были на проезды по памяти. Детальное исследование одного из падений показало, что hard fault случается так как портится значение в регистре общего назначения r5, который используется компилятором внутри функции как базовый адрес для работы с периферией. Внутри функции r5 не обновляется (записывается константа при входе в функцию один раз). То есть предположение проезда по памяти отпадает.
Второе предположение что поведение ломают вложенные прерывания подтвердилось. Сделали все прерывания одинакового приоритета hard fault исчез.

Вроде как баг исчез и стоит порадоваться, но очень похоже на черную магию, так как логического объяснения такому поведению не можем дать. Сохранение регистров в стек и восстановление везде присутствует (как минимум тщательно проверил сохранение\восстановление контекста в функции где упал в hard fault и тела высокоприоритетного прерывания).

Кто-нибудь может дать теоретически обоснованную модель такому поведению, чтобы понять куда еще стоит посмотреть?
Go to the top of the page
 
+Quote Post
 
Start new topic
Ответов
xelax
сообщение Jun 22 2016, 14:12
Сообщение #2


Местный
***

Группа: Свой
Сообщений: 370
Регистрация: 7-11-06
Пользователь №: 22 035



Убрал опцию --use_frame_pointer, вернул вложенные прерывания, оставил максимальную оптимизацию --O3. Hard fault исчезли.
Вернул опцию, буквально несколько секунд и софт падает в Hard fault.

Спасибо, судя по всему, действительно идет некорректная работа со стеком с включенной опцией.
Go to the top of the page
 
+Quote Post
romas2010
сообщение Jun 22 2016, 15:36
Сообщение #3


Участник
*

Группа: Участник
Сообщений: 63
Регистрация: 25-11-11
Пользователь №: 68 515



Цитата(xelax @ Jun 22 2016, 17:12) *
Убрал опцию --use_frame_pointer, вернул вложенные прерывания, оставил максимальную оптимизацию --O3. Hard fault исчезли.
Вернул опцию, буквально несколько секунд и софт падает в Hard fault.

Спасибо, судя по всему, действительно идет некорректная работа со стеком с включенной опцией.


Фишка вот в чем
непонятно зачем кейл двигает указатель стека SP на FP в командах
mov sp,fp
sub sp,#const

Если между этими командами возникнет прерывание,стек будет уже смещен,и контекст возникшего прерывания затрет контекст,сохраненный ранее при входе..я понимаю,мои объяснения звучат сумбурно,но возьмите лист бумаги,разрисуйте стек,идите по коду,там,где есть в командах использование sp и fp, то "разрисовывайте" эти регистры,и вы увидите....учитывайте,что стек растет ото дна

stmdb sp!,{r0...lr} -> sp=sp-4;RAM[sp]=r0 и т.д.
ldmia sp!,{r0..lr}-> r0=RAM[sp]; sp=sp+4

Я вам скажу,это реальный глюк..я в свое время неделю не мог понять,что с моей программой,а потом матерился на кейл десятиэтажным матом

Сообщение отредактировал romas2010 - Jun 22 2016, 15:53
Go to the top of the page
 
+Quote Post



Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 22nd July 2025 - 16:42
Рейтинг@Mail.ru


Страница сгенерированна за 0.01361 секунд с 7
ELECTRONIX ©2004-2016