|
Прерывания в Cortex-M3 |
|
|
|
Nov 24 2011, 02:31
|
Участник

Группа: Участник
Сообщений: 36
Регистрация: 5-12-10
Пользователь №: 61 414

|
Добрый день! Возникла следующая интересная проблема. По ходу выполнения прошивки в какой то момент происходит зацикливание программы на прерывании от USART1. То есть выполняется запуск обработчика прерываний с частотой примерно 100 кГц. Основная программа успевает сделать несколько инструкций после чего снова происходит прерывание. При этом если остановить обработку прерывания отладчиком и походить по инструкциям нормальный ход программы восстанавливается. Прерывания разрешены только на прием, флаг готовых данных не взведен. В регистре NVIC->ICSR указывается что активное прерывание от usart1. С чем может быть связанно такое поведение? Осциллографом контролировал линию - стабильная единица на обоих линиях. Стабильно повторяется. Прерывания по приему не запрещается и разрешено постоянно. Код void USART1_IRQHandler (void) { VD3R_ON; VD3G_ON;
if (USART_GetITStatus(USART1,USART_IT_TXE)) { // USART_ClearITPendingBit(USART1,USART_IT_TXE);
} if (USART_GetITStatus(USART1,USART_IT_RXNE)) { // USART_ClearITPendingBit(USART1,USART_IT_RXNE);
unsigned char receive_char=USART_ReceiveData(USART1);
if (!modemmode) {
}
VD3R_OFF; VD3G_OFF; }
|
|
|
|
|
 |
Ответов
|
Nov 24 2011, 05:31
|
Участник

Группа: Участник
Сообщений: 26
Регистрация: 15-11-07
Пользователь №: 32 363

|
Цитата(1kvi1 @ Nov 24 2011, 05:31)  Добрый день!
Возникла следующая интересная проблема.
По ходу выполнения прошивки в какой то момент происходит зацикливание программы на прерывании от USART1.
То есть выполняется запуск обработчика прерываний с частотой примерно 100 кГц.
Основная программа успевает сделать несколько инструкций после чего снова происходит прерывание. ... не любит STM чтобы использовали код не так, как в их примерах)). Заметил тоже самое с другими прерываниями. Например с таймером, вот такой код работает нормально: Код void TIM4_IRQHandler(void) { if (TIM_GetITStatus(TIM4, TIM_IT_Update) != RESET) { //здесь обработчик прерывания
} } а теперь для теста добавим пару переменных Код void TIM4_IRQHandler(void) { CountTest1++; if (TIM_GetITStatus(TIM4, TIM_IT_Update) != RESET) { //здесь обработчик прерывания CountTest2++; } } В этом случае все рассыпается, переменная CountTest1 будет постоянно быстрее накапливаться, чем переменная CountTest2. Это говорит о том, что void TIM4_IRQHandler(void) вызывается намного чаще, чем планировалось. Но вот такой код: Код void TIM4_IRQHandler(void) { if (TIM_GetITStatus(TIM4, TIM_IT_Update) != RESET) { //здесь обработчик прерывания CountTest2++; } CountTest1++; } работает нормально и CountTest1 всегда равна CountTest2. Получается, что вставка кода до строки if (TIM_GetITStatus(TIM4, TIM_IT_Update) != RESET) все ломает. Это одинаково проявляется на STM32F207 и STM32F407. Для эксперимента пробовал добавить GPIOC->ODR ^= GPIO_Pin_13; и посмотреть осциллографом длительность на GPIO_Pin_13. Получается полный хаос. 150 мс прерывания работают как положено раз в 1 мс (таймер настроен на 1 мс), потом на 150 мс висит 0 на GPIO_Pin_13. Может зависнуть на 150 мс и с 1 на выходе GPIO_Pin_13. Код void TIM4_IRQHandler(void) { GPIOC->ODR ^= GPIO_Pin_13; //индицируем прерывание для отладки if (TIM_GetITStatus(TIM4, TIM_IT_Update) != RESET) { //здесь обработчик прерывания CountTest2++; }
} опять же, если GPIOC->ODR ^= GPIO_Pin_13, добавить после строки if (TIM_GetITStatus(TIM4, TIM_IT_Update) != RESET), то все оживает и работает как положено.
Сообщение отредактировал vptr - Nov 24 2011, 05:32
|
|
|
|
|
Nov 24 2011, 05:58
|
Участник

Группа: Участник
Сообщений: 26
Регистрация: 15-11-07
Пользователь №: 32 363

|
да и обработка прерывания завершается TIM_ClearITPendingBit(TIM4, TIM_IT_Update) все как в примерах Код void TIM4_IRQHandler(void) { GPIOC->ODR ^= GPIO_Pin_13; //индицируем прерывание для отладки if (TIM_GetITStatus(TIM4, TIM_IT_Update) != RESET) { //здесь обработчик прерыания CountTest2++; TIM_ClearITPendingBit(TIM4, TIM_IT_Update); } }
Сообщение отредактировал vptr - Nov 24 2011, 06:02
|
|
|
|
|
Nov 24 2011, 08:37
|
Знающий
   
Группа: Участник
Сообщений: 643
Регистрация: 29-05-09
Из: Германия
Пользователь №: 49 725

|
Цитата(vptr @ Nov 24 2011, 07:58)  да и обработка прерывания завершается TIM_ClearITPendingBit(TIM4, TIM_IT_Update) все как в примерах Код void TIM4_IRQHandler(void) { GPIOC->ODR ^= GPIO_Pin_13; //индицируем прерывание для отладки if (TIM_GetITStatus(TIM4, TIM_IT_Update) != RESET) { //здесь обработчик прерыания CountTest2++; TIM_ClearITPendingBit(TIM4, TIM_IT_Update); } } В форуме здесь, а также на форуме ST, было упомянуто вообще-то для всех Кортексов (поищите сами), что при сбросе флагов прерываний непосредственно перед выходом из ISR, возможен повторный вызов ISR по причине конвейера и особенностей доступа по внутренним шинам. Поэтому перенесите TIM_ClearITPendingBit(TIM4, TIM_IT_Update); в начало ветви обработки, то есть поместив рабочие инструкции между сбросом флага и выходом из ISR.
|
|
|
|
|
Nov 24 2011, 08:50
|

неотягощённый злом
     
Группа: Свой
Сообщений: 2 746
Регистрация: 31-01-08
Из: Санкт-Петербург
Пользователь №: 34 643

|
Цитата(KnightIgor @ Nov 24 2011, 12:37)  В форуме здесь, а также на форуме ST, было упомянуто вообще-то для всех Кортексов (поищите сами), что при сбросе флагов прерываний непосредственно перед выходом из ISR, возможен повторный вызов ISR по причине конвейера и особенностей доступа по внутренним шинам. Поэтому перенесите TIM_ClearITPendingBit(TIM4, TIM_IT_Update); в начало ветви обработки, то есть поместив рабочие инструкции между сбросом флага и выходом из ISR. Познавательно. А сколько тактов интересно нужно чтобы всё успело всосаться? И почему-бы писателям этой либы сразу было не засунуть в ClearITPendingBit нужное кол-во нопов, чтоб мозги не компостировать никому....
--------------------
“Будьте внимательны к своим мыслям - они начало поступков” (Лао-Цзы)
|
|
|
|
|
Nov 24 2011, 09:34
|
Знающий
   
Группа: Участник
Сообщений: 643
Регистрация: 29-05-09
Из: Германия
Пользователь №: 49 725

|
Цитата(demiurg_spb @ Nov 24 2011, 10:50)  Познавательно. А сколько тактов интересно нужно чтобы всё успело всосаться? И почему-бы писателям этой либы сразу было не засунуть в ClearITPendingBit нужное кол-во нопов, чтоб мозги не компостировать никому.... Вот тут кое-что упоминается, в частности: Цитата As Andrew noted before, the reason is that this wouldn't be an erratum. It is a feature inherent in the architecture. I'll spare you the details, but simply put, Cortex-M3 has two independent bus interfaces for instructions and data respectively. Your memory access is using the data port (and waits for the APB bus cycle to finish), while the instruction port keeps fetching more code which gets executed. The ISR return might execute before the data bus access has completed, so NVIC thinks that the (still) active IRQ was a new one.
Сообщение отредактировал KnightIgor - Nov 24 2011, 09:38
|
|
|
|
Сообщений в этой теме
1kvi1 Прерывания в Cortex-M3 Nov 24 2011, 02:31 demiurg_spb Думаю что это связано с тем что запросы на прерыва... Nov 24 2011, 04:44 1kvi1 ТО что флаги автоматически сбрасываются - это мне ... Nov 24 2011, 05:15 demiurg_spb Цитата(vptr @ Nov 24 2011, 09:31) не люби... Nov 24 2011, 05:36  AHTOXA Возможно, это то, что называется "spurious in... Nov 24 2011, 06:08   vptr Цитата(KnightIgor @ Nov 24 2011, 11:37) В... Nov 24 2011, 09:52    demiurg_spb Цитата(vptr @ Nov 24 2011, 13:52) и тольк... Nov 25 2011, 04:37     dxp Цитата(demiurg_spb @ Nov 25 2011, 11:37) ... Nov 25 2011, 06:34      demiurg_spb Цитата(dxp @ Nov 25 2011, 10:34) А не пом... Nov 25 2011, 06:58       dxp Цитата(demiurg_spb @ Nov 25 2011, 13:58) ... Nov 25 2011, 15:21 andrewlekar А по-моему никто ничего не рушит, а просто прерыва... Nov 24 2011, 05:42 1kvi1 "spurious interrupt" - да был такой опыт... Nov 24 2011, 08:53 ViKo А чего-й-то у меня прерывание работает простенько?... Nov 25 2011, 12:04 demiurg_spb Цитата(ViKo @ Nov 25 2011, 16:04) А чего-... Nov 28 2011, 08:01  ViKo Цитата(demiurg_spb @ Nov 28 2011, 11:01) ... Nov 28 2011, 08:50 1kvi1 К сожалению, описанные выше ситуации, когда флаг з... Nov 27 2011, 15:33 dxp Цитата(1kvi1 @ Nov 27 2011, 22:33) Интере... Nov 27 2011, 16:24 V_M_Luck ЦитатаПоэтому, имхо, грамотный подход - это исполь... Dec 8 2011, 10:13 1kvi1 Внимательное чтение документации помогло определит... Dec 9 2011, 09:54
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|