И снова о таймере

Buldakov
Offline
Зарегистрирован: 17.01.2016

У меня вопрос:

Можно ли сделать делитель на таймере для Arduino UNO для входной частоты и поделенную частоту выдать на выход? Может кто нибудь посоветовать ссылку на проекты, где это реализовано?

Например на выв.5 подаем частоту 100кгц. Делитель делаем равным 12 и на выв.3 получаем частоту 8 кгц.

b707
Offline
Зарегистрирован: 26.05.2017

чисто теоретически - выбираем для таймера тактирование с внешнего входа, запускам режим по совпадению, в регистр сравнения пишем половину делителя (в вашем примере 8/2 = 4) и по совпадению инвертим уровень нужного выхода

Правда сомневаюсь. что Уно такое умеет

sadman41
Offline
Зарегистрирован: 19.10.2016

Timer/Counter2 на ATMega328 со внешним тактированием.

SLKH
Offline
Зарегистрирован: 17.08.2015

Вар1: В прерывании считаем фронты входной частоты и инвертируем выходной пин. При 100 килогерцах другими тяжелыми задачами не занимаемся.
Вар2: Лепим рядом счетчик на 561*/CD40*.

dimax
dimax аватар
Offline
Зарегистрирован: 25.12.2013

У первого таймера тактирование от внешнего входа -штатный режим (битыCS10..CS12) + режим CTC и вуаля.

Buldakov
Offline
Зарегистрирован: 17.01.2016

По 1 варианту: Прерывание уже занято. Максимальная частота по измерению прерывания 250 кгц. и уже работает. Таймер 1 уже тоже занят. Остается свободным только таймер 2 или внешний счетчик (555ИЕ8 с задаваемым коэф. деления). Хочу повысить максимальную частоту для прерывания. Например на вход счетчика подаем 2500 кгц на таймере его делим на 10 и подаем на вход прерывания.

Пока делаю пробный вариант на 1 таймере СТС режим для встроенного кварца. Это вариант работает.

//---Частота генератора 64000 Гц.----------------------------------------------//
void setup() {                                                                 //
pinMode(9, OUTPUT);                                                            //
//---Настройка таймера 1-------------------------------------------------------//
TCCR1A = 1<<COM1A0;// Переключение пина 9 по сравнению                         //
TCCR1B = 0;                                                                    //
TCNT1  = 0;                                                                    //
OCR1A=124;    //отсчитать 125 входных импульсов до сравнения                   //
TCCR1B = (0 << CS12)|(0 << CS11)|(1 << CS10)|(1<<WGM12);//прескалер=1.CTC mode //
}                                                                              //
void loop()                                                                    //
{}                                                                             //
//-----------------------------------------------------------------------------//

Вот вариант для 2 таймера вроде все тоже самое , но не работает.

//---Частота генератора 64000 Гц.----------------------------------------------//
void setup() {                                                                 //
pinMode(11, OUTPUT);                                                           //
pinMode(3, OUTPUT);                                                            //
pinMode(9, OUTPUT);                                                            //
//---Настройка таймера 2-------------------------------------------------------//
TCCR2A = 0; //  обнуляю регистр                                                //
TCCR2B = 0; //  обнуляю регистр                                                //
TCNT2 = 0; //ensures counter value starting from zero                          //
OCR2A = 250; //compare match register for timer2                               //
TCCR2A = (1<<WGM21);  // Configure timer 2 for CTC mode                        //
TCCR2B = (0<<CS22) |(0<<CS21)| (1<<CS20); // prescaler 1                       //
//---Настройка таймера 1-------------------------------------------------------//
TCCR1A = 1<<COM1A0;//                                                          //
TCCR1B = 0;                                                                    //
TCNT1  = 0;                                                                    //
OCR1A=124;    //отсчитать 125 входных импульсов до сравнения                   //
TCCR1B = (0 << CS12)|(0 << CS11)|(1 << CS10)|(1<<WGM12);//прескалер=1.CTC mode //
}                                                                              //
void loop()                                                                    //
{}                                                                             //
//-----------------------------------------------------------------------------//

 

dimax
dimax аватар
Offline
Зарегистрирован: 25.12.2013

Buldakov, во-первых не ясно как приведённые примеры соотносятся с задачей. В задаче надо делить внешний сигнал -а тут вы делите внутреннюю частоту тактирования. Во втором примере вы результат сравнения никуда не выводите (не активны биты Compare Match Output)

SLKH
Offline
Зарегистрирован: 17.08.2015

Buldakov пишет:

По 1 варианту: Прерывание уже занято.

Все 20 заняты?

Цитата:
Максимальная частота по измерению прерывания 250 кгц. и уже работает.
Интересно, что там за 4 микросекунды работает.

Buldakov
Offline
Зарегистрирован: 17.01.2016

Вроде с внутреннего генератора получилось. Выходной сигнал на выв.11

//---Частота генератора 64000 Гц.----------------------------------------------//
void setup() {                                                                 //
pinMode(11, OUTPUT);                                                           //
//---Настройка таймера 2-------------------------------------------------------//
TCCR2A = 0; //  обнуляю регистр                                                //
TCCR2B = 0; //  обнуляю регистр                                                //
TCNT2  = 0; //ensures counter value starting from zero                         //
OCR2A  = 124; //отсчитать 125 входных импульсов до сравнения                   //
TCCR2A = (0<<COM2A1)|(1<<COM2A0);//                                            //
TCCR2A|= (1<<WGM21);// Configure timer 2 for CTC mode                          //
TCCR2B = (0<<CS22) |(0<<CS21)| (1<<CS20); // prescaler 1                       //
//-----------------------------------------------------------------------------//
}                                                                              //
void loop()                                                                    //
{}                                                                             //
//-----------------------------------------------------------------------------//

Теперь буду пробовать запустить таймер от внешнего генератора. Как я понял

Бит EXCLK (6) регистра ASSR разрешает использование внешнего тактового сигнала от кварцевого резонатора 32 кГц при записи в него 1.

Бит  AS2 (5) регистра ASSR управляет способом тактирования (1 - от внешнего резонатора 32 кГц, подключенного к TOSC1 (9 ножка) / 0 - от внутреннего генератора CLK).

http://avrprog.blogspot.com/2013/03/t2-8.html

 

Buldakov
Offline
Зарегистрирован: 17.01.2016

Вопрос решился. Входная частота подается на выв. 9. Только жалко что таймер не может делить входную частоту меньше чем в в 2 раза и время выполнения кода зависит от измеряемой частоты. Поэтому перехожу на внешний делитель с логикой и 555ИЕ8 +555ИЕ10. Частотка при этом будет измеряться от 1 гц до 20 мгц для советских счетчиков и до 80мгц для импортных. Зато радиолюбители освоят изготовление и травление печатных плат в качестве добавки к Arduino Uno. Буду делать частотомер, как проще и удобнее для себя. А если кому то будет сложно, то это не ко мне.

//---Частота генератора деленная на125 выход выв.11----------------------------//
void setup() {                                                                 //
pinMode(11, OUTPUT);                                                           //
//---Настройка таймера 2-------------------------------------------------------//
TCCR2A = 0; //  обнуляю регистр                                                //
TCCR2B = 0; //  обнуляю регистр                                                //
ASSR   = 0; //  обнуляю регистр                                                //
TCNT2  = 0; //ensures counter value starting from zero                         //
TIMSK2 = (1<<TOIE2);         //прерывание по переполнению таймера 2            //
OCR2A  = 124; //отсчитать 125 входных импульсов до сравнения                   //
TCCR2A = (0<<COM2A1)|(1<<COM2A0);//                                            //
TCCR2A|= (1<<WGM21);// Configure timer 2 for CTC mode                          //
TCCR2B = (0<<CS22) |(0<<CS21)| (1<<CS20); // prescaler 1                       //
ASSR   = (1<<EXCLK)|(1<<AS2);                                                  //
//-----------------------------------------------------------------------------//
}                                                                              //
void loop()                                                                    //
{}                                                                             //
//-----------------------------------------------------------------------------//