Не работает ШИМ на ATMEGA168
Добавлено: Вт мар 06, 2018 22:32:15
Привет, коллеги!
Есть проект на ATMEGA8, ШИМ которого удачного работал. Сейчас появилась другая задумка, взял другой МК, а именно ATMEGA168P, взял кусок кода с ШИМом, поправил регистры и опа, а он не работает. Точнее прерывание по переполнению таймера есть, а вот то что в прерывании находится, выполняться не хочет. Вот весь код, который должен включить RGB светодиод:
Если раскомментировать PORTB = 0x02, то светодиод включается, но оставшийся кусок кода не работает, хотя этот же кусок кода в Атмега8 норм работает, а в нём никаких регистров и прочего несовместимого с Атмега168 не вижу
Есть проект на ATMEGA8, ШИМ которого удачного работал. Сейчас появилась другая задумка, взял другой МК, а именно ATMEGA168P, взял кусок кода с ШИМом, поправил регистры и опа, а он не работает. Точнее прерывание по переполнению таймера есть, а вот то что в прерывании находится, выполняться не хочет. Вот весь код, который должен включить RGB светодиод:
Код: Выделить всё
#define F_CPU 8000000UL
#include <avr/io.h>
#include <util/delay.h>
#include <avr/interrupt.h>
#include "type_var.h"
#define RED PORTB1
#define GREEN PORTB2
#define BLUE PORTB3
uint8_t counter=0;
uint8_t lev_red, lev_green, lev_blue;
uint8_t buf_lev_ch1, buf_lev_ch2, buf_lev_ch3;
int main(void)
{
PORTB = 0x00;
DDRB=0b00001110; // установка PortB пины 0,1,2 выходы
TIMSK0 |= (1 << TOIE0); // включить прерывание по переполнению таймера
TIMSK0 |= (1 << OCIE0A);
TCCR0B = 0b00000001; // настройка таймера, делитель выкл
sei(); // разрешить прерывания
while (1)
{
lev_red=255;lev_green=200;lev_blue=20; //яркость каждого светодиода в RGB
}
}
ISR (TIMER0_OVF_vect) //обработка прерывания по переполнению таймера
{
//PORTB = 0x02;
if (++counter==0) //счетчик перехода таймера через ноль
{
buf_lev_ch1=lev_red; //значения длительности ШИМ
buf_lev_ch2=lev_green;
buf_lev_ch3=lev_blue;
PORTB |=(1<<RED)|(1<<GREEN)|(1<<BLUE); //подаем 1 на все каналы
}
if (counter==buf_lev_ch1) PORTB&=~(1<<RED); //подаем 0 на канал
if (counter==buf_lev_ch2) PORTB&=~(1<<GREEN); //по достижении
if (counter==buf_lev_ch3) PORTB&=~(1<<BLUE); //заданной длительности.
}