Форум программистов, компьютерный форум, киберфорум
Наши страницы
Микроконтроллеры Atmega AVR
Войти
Регистрация
Восстановить пароль
 
Рейтинг 4.74/19: Рейтинг темы: голосов - 19, средняя оценка - 4.74
kottos
0 / 0 / 0
Регистрация: 10.12.2014
Сообщений: 1
1

ATMega88 - 10 PWM

13.12.2014, 23:22. Просмотров 3593. Ответов 4
Метки нет (Все метки)

Доброго времени суток, Уважаемые!

Имею задачу сделать 10 ШИМ со следующими характеристиками:
— Кол-во шагов 1000
— Минимальная длинна импульса 10us
— Максимальная длинна импульса 1000us
— Тактовая чистота 100Hz

Решать задачу я принялся через 8-ми битный таймер.
Вот пример кода
Код
// Atmega88PU

#include <avr/io.h>
#define F_CPU 8000000
#include <avr/interrupt.h>
#include <util/delay.h>

void confikure_pwm() {
TIMSK0 |= (1 << TOIE0); // Enable overflow interrupt
TCCR0A |= (1<<WGM00) | (1<<WGM01);
TCCR0B |= (1<<CS00); // divide by as is
sei();
}

int main(void) {
confikure_pwm();
for (;;) {
continue;
}
}

volatile uint8_t pwm_speed[4] = {0};
volatile uint8_t pwm_pin[4] = {PORTC4, PORTD2, PORTD4, PORTD6};
volatile uint8_t * pwm_port[] = {&PORTC, &PORTD, &PORTD, &PORTD};
volatile uint8_t counter = 0x0;

ISR(TIMER0_OVF_vect)
{
if (counter == 0xFF) {
counter = 0x0;
for (int i=0;i<=4;i++) {
if (pwm_speed[i] != 0x00) {
*pwm_port[i] |= (1 << pwm_pin[i]);
}
}
return;
}
for (int i=0;i<=4;i++) {
if (pwm_speed[i] == counter) {
*pwm_port[i] |= (0 << pwm_pin[i]);
}
}
counter++;
}
Ввиду того что новичок в С и в AVR то имею ряд вопросов:
1) Правильно ли я делаю?
2) Не будет ли отжирать 99.9% процесорного времени данная конструкция ?
3) Как делать правильно?
0
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
13.12.2014, 23:22
Ответы с готовыми решениями:

ATmega88
Нужно к 5 портам подключить светодиоды. Код написал, моделирую в SimulIDE. start: ldi r16,...

Bootloader atmega88
Всем привет. Весь день уже бьюсь над этим загрузчиком. Шью вот это:...

Прерывание INT0 Atmega88
Пытаюсь использовать прерывание INT0. В avr studio и протеусе все работает хорошо, но в железе...

atmega88 не работает FOC1A
Выполняю следующий код: unsykned int duration = 2500; unsykned int freq_temp = 10000; ...

Atmega88 + UART = проблема
Приветствую! Пытаюсь соединить два камня по USORT интерфейсу. Для тактирования в обоих камнях...

4
dimyurk1978
0 / 0 / 0
Регистрация: 07.02.2106
Сообщений: 3,047
14.12.2014, 07:19 2
МК AVR плохо подходят для многоканального ШИМ-а. Так как расход процессорного времени большой. Времени на другие задачи практически не остается.
Поэтому, если вам нужно управлять 10 светодиодами, то вам нужен BAM. Ссылка.
0
Tistir500
0 / 0 / 0
Регистрация: 06.02.2013
Сообщений: 333
14.12.2014, 10:09 3
Есть полезная программка - "AVR IO Desykner", в ней можно быстро посмотреть настройки периферии.
По приведенным в коде настройкам (рабочая частота контроллера - 8Мгц #define F_CPU 8000000) имеем:
Timer_0; режим Fast PWM, 8-bit TOP=0xFF; Частота таймера (период ШИМ) 31.25 кГц
Дальше каша. Нужно использовать или аппаратный ШИМ, но тогда у данного таймера всего 2 канала и кол-во шагов 255 (таймер 8 битный), или делать программный. По условиям ТЗ подходит только программый. На форуме уже много раз приводили примеры программного ШИМа, я давал ссылку на описание алгоритма у самого ATMEL
Если кратко - нужно настроить таймер на режим CTC, частота= Максимальная длинна импульса 1000us=1ms=1кГц*(Кол-во шагов 1000) = 1Мгц. При частоте контроллера 8Мгц на обработку кода в прерывании остается 6 команд (оверхед - войти в прерывание и выйти оттуда). Вывод - нужно урезать осетра до 255 шагов и поднять "Максимальная длинна импульса" до 100Гц, увеличить частоту контроллера до максимальной.
0
mShit
0 / 0 / 0
Регистрация: 12.08.2012
Сообщений: 1,217
14.12.2014, 13:05 4
Если 10 каналов с максимальной шириной импульса 1мс и периодом 10мс то напрашивается мысль формировать каналы последовательно, если это не критично для задачи, либо это можно довольно изящно и нересурсоёмко сделать как у Di Halt`а в этой статье.
0
SOKPOWIHIU
0 / 0 / 0
Регистрация: 11.07.2014
Сообщений: 116
15.12.2014, 00:52 5
Есть полезная программка - "AVR IO Desykner", в ней можно быстро посмотреть настройки периферии.
По приведенным в коде настройкам (рабочая частота контроллера - 8Мгц #define F_CPU 8000000) имеем:
Timer_0; режим Fast PWM, 8-bit TOP=0xFF; Частота таймера (период ШИМ) 31.25 кГц
Дальше каша.
Ну и толку с такой программы? Поделить 8000000 на 256 можно на любом калькуляторе.
А рассчитать, сколько тактов длится прерывание поможет отладчик.
Если 10 каналов с максимальной шириной импульса 1мс и периодом 10мс
Автор ошибся, максимальное заполнение ШИМ не 10%, а 100%.
0
15.12.2014, 00:52
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
15.12.2014, 00:52

Проблема с UART (ATmega88)
Добрый день! Уже долгое время пытаюсь разобраться с работой uart. Наваял программу, по которой мк...

Переключение каналов АЦП atmega88
Добрый день. В который раз сталкиваюсь с АЦП на меге и никак не могу понять как правильно...

Внутренние защитные диоды ATmega88?
Друзья, подскажите кто реально знает, внутренние защитные диоды легко выдержат через 50кОм...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
5
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2019, vBulletin Solutions, Inc.
Рейтинг@Mail.ru