Помощь - Поиск - Пользователи - Календарь
Полная версия этой страницы: mega8 timer...
Форум разработчиков электроники ELECTRONIX.ru > Микроконтроллеры (MCs) > AVR
BVU
Всем, привет!
Для mega8 пытаюсь сделать прерывание по сравнению - используя 16-bit timer-B. Выполняю инициализацию, таймер начинает работать увеличивая программный счетчик в теле своего прерывания, но работа идет явно не по сравнению константного значения, а как бы по переполнению... Почему такие выводы спросите вы, потому что при изменении константы в регисте сравнения в два раза - частота прерываний не меняется... sad.gif. По всей видимости где-то, что-то я не доглядел или непонял.
Привожу пример своего кода:

void InitTimers(void)
{
/* Initialization Timer1 */
OCR1B = QUARTER_sec; // Set compare value on one second.
TIMSK = (1 << OCIE1B); // Set mask to enable Timer1B compare interrupt.
TCCR1B = ((1 << CS12) | (1 << CS10)); // Set prescaller on 1024.
}


// IRQ TIMER1_COMPB
#pragma vector = TIMER1_COMPB_vect
__interrupt void timer1_compB_Processing(void)
{
char pd;

__disable_interrupt();
tick++;
... // обработка подпрограммы.
__enable_interrupt();
}

Ваши мнения корифеи программирования таймеров???

С уважением,
BVU
she
Цитата(BVU @ Aug 17 2005, 14:01)
/* Initialization Timer1 */
    OCR1B = QUARTER_sec;    // Set compare value on one second.
    TIMSK = (1 << OCIE1B);    // Set mask to enable Timer1B compare interrupt.
    TCCR1B = ((1 << CS12) | (1 << CS10));    // Set prescaller on 1024.


*


а режим в битах WGM10:3 дядя устанавливать будет?=)
prottoss
Цитата(she @ Aug 17 2005, 18:21)
Цитата(BVU @ Aug 17 2005, 14:01)

/* Initialization Timer1 */
    OCR1B = QUARTER_sec;    // Set compare value on one second.
    TIMSK = (1 << OCIE1B);    // Set mask to enable Timer1B compare interrupt.
    TCCR1B = ((1 << CS12) | (1 << CS10));    // Set prescaller on 1024.


*


а режим в битах WGM10:3 дядя устанавливать будет?=)
*



Если таймер работает просто в режиме счетчика, а не в режиме WGM, то эти биты трогать не надо
prottoss
Цитата(BVU @ Aug 17 2005, 18:01)
Всем, привет!
Для mega8 пытаюсь сделать прерывание по сравнению  - используя 16-bit timer-B. Выполняю инициализацию, таймер начинает работать увеличивая программный счетчик в теле своего прерывания, но работа идет явно не по сравнению константного значения, а как бы по переполнению... Почему такие выводы спросите вы, потому что при изменении константы в регисте сравнения в два раза - частота прерываний не меняется... sad.gif.  По всей видимости где-то, что-то я не доглядел или непонял.
Привожу пример своего кода:

void InitTimers(void)
{
/* Initialization Timer1 */
    OCR1B = QUARTER_sec;    // Set compare value on one second.
    TIMSK = (1 << OCIE1B);    // Set mask to enable Timer1B compare interrupt.
    TCCR1B = ((1 << CS12) | (1 << CS10));    // Set prescaller on 1024.
}
*


Если Вы меняете константу сравнения, то частота прерываний не изменится, если Вы не установите бит WGM12(СTC) (сброс по совпадению ТС1) - но он работает только для OCR1A, а Ваш код для OCR1В. По этому частота прерываний менятся не будет. Вы только смещаете во времени начало прерывания от сброса счетчика в 0x0000.
Мой Вам совет - проэмулируйте все в AVRStudio - и все всанет на свои места.

Цитата(BVU @ Aug 17 2005, 18:01)
// IRQ TIMER1_COMPB
#pragma vector = TIMER1_COMPB_vect
__interrupt void timer1_compB_Processing(void)
{
char pd;

    __disable_interrupt();
    tick++;
    ...  // обработка подпрограммы.
    __enable_interrupt();
}

Ваши мнения корифеи программирования таймеров???

С уважением,
BVU
*


__disable_interrupt(); __enable_interrupt(); - это не нужно, при входе в прерывние бит глобальных прерываний автоматически сбрасывается. Так что это пустое.
BVU
По всей видимости после прерывания на совпадение счетчик TCNT1 продолжает счет до 0xffff и сбросившись в 0x0000 работа продолжается до следующего совпадения. Тем самым создается иллюзия, что таймер работает по переполнению и не зависит от константы сравнения.
В этом случае в самом начале обработки прерывания таймера придется обнулять TCNT1 "в ручную" (высокой точности периода мне пока не требуется, ну а если возникнет такая необходимость ее можно компенсировать ассемблерными вставками - nop) или воспользоваться советом prottoss.

Тем не менее всем участникам спасибо за помощь!

С уважением,
BVU
yung
Лучше будет использовать режим СТС - сброс при совпадении. Почитай pdf, там это есть.
prottoss
Цитата(yung @ Aug 18 2005, 02:33)
Лучше будет использовать режим СТС - сброс при совпадении. Почитай pdf, там это есть.
*


Только, в таком случае, не забудь в качестве регистра по совпадению использовать OCR1А
arttab
Сделайте как сказано выше - на OCR1А. Проверено - работает.
OCR1A = 0x001E;
TCCR1B = 0x0D; //0D no filt. capt. wave. 8E6/1024 (00000101)=781.5
и соответственно #pragma vector=TIMER1_COMPA_vect
Сам разбирался в даташите и чтобы развеять сомнения воспользовался мастеров в кодевижене.
Для просмотра полной версии этой страницы, пожалуйста, пройдите по ссылке.
Invision Power Board © 2001-2025 Invision Power Services, Inc.