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

 
 
> прерывание по таймеру, stm32f4xx
xheli
сообщение Jan 24 2012, 15:25
Сообщение #1





Группа: Участник
Сообщений: 14
Регистрация: 24-01-12
Пользователь №: 69 851



Пробую сделать обычный таймер, вроде работает, но вот первое прерывание вызывается сразу же после старта.
Т.е. настраиваю таймер на 5 секунд, делаю TIM_Cmd(TIM7, ENABLE), запускаю, микропроцессор стартует и сразу же срабатывает прерывание, затем все как надо, каждые пять секунд или сколько задам.
Как сделать, чтобы не было первого "ложного" срабатывания? Запустил проц и только через N сек сработало.
Вот код:
CODE

TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
NVIC_InitTypeDef NVIC_InitStructure;

RCC_APB1PeriphClockCmd ( RCC_APB1Periph_TIM7, ENABLE );

NVIC_InitStructure.NVIC_IRQChannel = TIM7_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);

TIM_TimeBaseStructure.TIM_Period = ms * 2;
TIM_TimeBaseStructure.TIM_Prescaler = ( uint16_t ) ( SystemCoreClock / APB1_PRESCALER * 2 / 2000 ) - 1;
TIM_TimeBaseStructure.TIM_ClockDivision = 0;
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;
TIM_TimeBaseInit ( TIM7, &TIM_TimeBaseStructure );

TIM_ITConfig ( TIM7, TIM_IT_Update, ENABLE );
TIM_Cmd ( TIM7, ENABLE );


и обработчик прерывания:

CODE

void TIM7_IRQHandler ( void )
{
if ( TIM_GetITStatus ( TIM7, TIM_IT_Update ) != RESET )
{
TIM_ClearITPendingBit ( TIM7, TIM_IT_Update );
}

...
}


Микропроцессор stm32f417

Сообщение отредактировал xheli - Jan 24 2012, 15:26


--------------------
Go to the top of the page
 
+Quote Post
 
Start new topic
Ответов (1 - 12)
klen
сообщение Jan 24 2012, 15:36
Сообщение #2


бессмертным стать можно тремя способами
*****

Группа: Свой
Сообщений: 1 405
Регистрация: 9-05-06
Из: Москва
Пользователь №: 16 912



первая мысль без обдумывания - а не занести ли в счетный регистр значение 1 перед пуском?
Go to the top of the page
 
+Quote Post
xheli
сообщение Jan 24 2012, 16:27
Сообщение #3





Группа: Участник
Сообщений: 14
Регистрация: 24-01-12
Пользователь №: 69 851



Цитата(klen @ Jan 24 2012, 19:36) *
первая мысль без обдумывания - а не занести ли в счетный регистр значение 1 перед пуском?

Т.е. такое поведение нормально?
TIM7->CNT = 1 не помогает, да и не правильно это.

Вот так работает:
Код
TIM_ClearITPendingBit ( TIM7, TIM_IT_Update );
TIM_ITConfig ( TIM7, TIM_IT_Update, ENABLE );
TIM_Cmd ( TIM7, ENABLE );


Сообщение отредактировал IgorKossak - Jan 24 2012, 18:11
Причина редактирования: [code]


--------------------
Go to the top of the page
 
+Quote Post
Aaron
сообщение Jan 25 2012, 07:32
Сообщение #4


Местный
***

Группа: Свой
Сообщений: 243
Регистрация: 5-10-06
Из: Зеленоград
Пользователь №: 21 007



я всегда и везде перед инициализацией прерываний очищаю сопутствующие флаги, и в аппнотах по-моему на все или почти все МК пишут так делать.
Go to the top of the page
 
+Quote Post
xheli
сообщение Jan 25 2012, 07:55
Сообщение #5





Группа: Участник
Сообщений: 14
Регистрация: 24-01-12
Пользователь №: 69 851



Цитата(Aaron @ Jan 25 2012, 11:32) *
я всегда и везде перед инициализацией прерываний очищаю сопутствующие флаги, и в аппнотах по-моему на все или почти все МК пишут так делать.

спасибо, буду внимательнее


--------------------
Go to the top of the page
 
+Quote Post
batisto4ka
сообщение Feb 20 2012, 14:56
Сообщение #6


Частый гость
**

Группа: Участник
Сообщений: 89
Регистрация: 3-01-11
Пользователь №: 61 997



Вопрос по таймерам в stm32. Не могу понять, почему преывание срабатывает через половину заданного интервала, то есть в 2 раза быстрее. Прерывания от таймера настроено на 1 сек, а срабатывает чрез 30 секунд. Настройки:
Код:
Код
void SpeedSensorNVICTmrInit    (void)
{
NVIC_InitTypeDef NVIC_InitStructure;
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_1);
NVIC_InitStructure.NVIC_IRQChannel = TIM5_IRQn;
    NVIC_InitStructure.NVIC_IRQChannelSubPriority =0;
    NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
    NVIC_Init(&NVIC_InitStructure);
    TIM_ITConfig(SSTIMER,TIM_IT_Update,ENABLE);
}
void    TIM5_IRQHandler    (void) // если сработало прерывание на 1 sec
{

if    (TIM_GetITStatus(TIM5,TIM_IT_Update))
    {
    TIM_ClearITPendingBit(TIM5,TIM_IT_Update);          //
    TmrOff();
          //do smth;
    TmrOn();
    }
}
void InitSpeedSensorTmr    (TIM_TypeDef* TIM,unsigned short delay)
{
TIM_TimeBaseInitTypeDef     Tim_InitStruct;
Tim_InitStruct.TIM_ClockDivision=TIM_CKD_DIV1;
Tim_InitStruct.TIM_CounterMode=TIM_CounterMode_Up;
Tim_InitStruct.TIM_Period=delay;         //    
Tim_InitStruct.TIM_Prescaler=35999;     //36MHz/(35999+1)=1000
TIM_TimeBaseInit(TIM,&Tim_InitStruct);

TmrOn();
}

Где
TIM=TIM5, delay=1000.
Используемый камень -stm32f107vet
Go to the top of the page
 
+Quote Post
AHTOXA
сообщение Feb 20 2012, 16:35
Сообщение #7


фанат дивана
******

Группа: Свой
Сообщений: 3 387
Регистрация: 9-08-07
Из: Уфа
Пользователь №: 29 684



Вот что написано в RM0008:
Цитата
1. if the APB prescaler is 1, the timer clock frequencies are set to the same frequency as
that of the APB domain to which the timers are connected.
2. otherwise, they are set to twice (×2) the frequency of the APB domain to which the
timers are connected.

То есть, если APB1 у вас молотит на 36МГц, то таймер - на 72МГц.


--------------------
Если бы я знал, что такое электричество...
Go to the top of the page
 
+Quote Post
ViKo
сообщение Feb 20 2012, 16:40
Сообщение #8


Универсальный солдатик
******

Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362



Цитата(batisto4ka @ Feb 20 2012, 17:56) *
Вопрос по таймерам в stm32. Не могу понять, почему преывание срабатывает через половину заданного интервала, то есть в 2 раза быстрее. Прерывания от таймера настроено на 1 сек, а срабатывает чрез 30 секунд.

Оно же sm.gif
http://electronix.ru/forum/index.php?showt...t&p=1029195
Go to the top of the page
 
+Quote Post
batisto4ka
сообщение Feb 21 2012, 12:12
Сообщение #9


Частый гость
**

Группа: Участник
Сообщений: 89
Регистрация: 3-01-11
Пользователь №: 61 997



проверила, прескаллер АРВ1 = 2.В чем тогда причина
Go to the top of the page
 
+Quote Post
ViKo
сообщение Feb 21 2012, 12:17
Сообщение #10


Универсальный солдатик
******

Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362



Цитата(batisto4ka @ Feb 21 2012, 15:12) *
проверила, прескаллер АРВ1 = 2.В чем тогда причина

В нем и есть... Внимательно изучите уже сказанное в ответ.
Go to the top of the page
 
+Quote Post
Sanya_kv
сообщение Feb 22 2012, 05:31
Сообщение #11


Частый гость
**

Группа: Свой
Сообщений: 185
Регистрация: 25-02-09
Из: Россия
Пользователь №: 45 369



Цитата
Вопрос по таймерам в stm32. Не могу понять, почему преывание срабатывает через половину заданного интервала, то есть в 2 раза быстрее. Прерывания от таймера настроено на 1 сек, а срабатывает чрез 30 секунд.

У меня была подобная проблема на STM32F2
Код
void TIM7_IRQHandler(void)
{
    if (TIM7->SR& TIM_SR_UIF)
    {
        ...
        //Почему-то не всегда сбрасывается, примерно через рас, иногда не регулярно.
        TIM7->SR = ~(uint16_t)TIM_SR_UIF;
        //if (TIM7->SR& TIM_SR_UIF)//Проверка. В системе только таймер, больше не чего.
        //    while(1);//ОСТОРОЖНО Ж

        //решил этим
        while (TIM7->SR& TIM_SR_UIF)
            TIM7->SR = ~(uint16_t)TIM_SR_UIF;
    }

}
Go to the top of the page
 
+Quote Post
Vichkins
сообщение Feb 23 2012, 08:37
Сообщение #12


Участник
*

Группа: Участник
Сообщений: 22
Регистрация: 11-02-09
Пользователь №: 44 714



Цитата(Sanya_kv @ Feb 22 2012, 08:31) *
У меня была подобная проблема на STM32F2
Код
void TIM7_IRQHandler(void)
{
    if (TIM7->SR& TIM_SR_UIF)
    {
        ...
        //Почему-то не всегда сбрасывается, примерно через рас, иногда не регулярно.
        TIM7->SR = ~(uint16_t)TIM_SR_UIF;
        //if (TIM7->SR& TIM_SR_UIF)//Проверка. В системе только таймер, больше не чего.
        //    while(1);//ОСТОРОЖНО Ж

        //решил этим
        while (TIM7->SR& TIM_SR_UIF)
            TIM7->SR = ~(uint16_t)TIM_SR_UIF;
    }

}


правильнее будет wink.gif
TIM7->SR &=~TIM_SR_UIF;

Сообщение отредактировал Vichkins - Feb 23 2012, 08:38
Go to the top of the page
 
+Quote Post
ViKo
сообщение Feb 23 2012, 10:03
Сообщение #13


Универсальный солдатик
******

Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362



Цитата(Vichkins @ Feb 23 2012, 11:37) *
правильнее будет wink.gif
TIM7->SR &=~TIM_SR_UIF;

Если посмотрите на состав регистра SR в базовых таймерах, то увидите, что достаточно будет
TIM7->SR = 0;
Аналогично, для проверки достаточно
while (!TIM7->SR)
Go to the top of the page
 
+Quote Post

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

 


RSS Текстовая версия Сейчас: 31st July 2025 - 03:50
Рейтинг@Mail.ru


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