Страница 1 из 2
помогите разобратся с таймером 1 на tiny2313
Добавлено: Вс май 26, 2013 23:31:07
Oleg7771
хотел сделать генератор импульсов на tiny2313, использую прерывания по совпадению CTC1, но частота на выходе в 4 раза меньше
чем должна быть.
TCCR1B=00001011 CTC1 + /64
OCR1AH=0
OCR1AL=1
TIMSK=0x40 (bit OCIE1A)
внутренний генератор 8МГц
делитель на 8 отключен
фузы CKSEL=0100 SUT=10
в обработчике прерываний инвертирую 0й бит порта B.
получается частота на выходе 31250 в место 125000 (8000000/64=125000)
помогите разобраться где происходит деление на 4?
проверял в PROTEUS'е и на реальном железе тоже самое.
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Вс май 26, 2013 23:36:37
shads
125000 случайно не для RFID нужна?
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Вс май 26, 2013 23:43:02
Oleg7771
shads писал(а):125000 случайно не для RFID нужна?
нет, я просто хотел сделать генератор для разных целей.
расчет брал из книги по AVR контроллерам, но не пойму или я чего то не понимаю, или там не правильно написано)
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Вс май 26, 2013 23:52:36
shads
так попробуй
Код: Выделить всё
OCR1A = 32; //число сравнения для таймера T1 для формирования прерываний с частотой 250000Гц
TIMSK = (1<<OCIE1A); //разрешить прерывание по совпадению T1
TCCR1A =(0<<WGM11)| (0<<WGM10); //режим таймера T1 = CTC сброс при совпадении
TCCR1B =(0<<WGM13)| (1<<WGM12)| //режим таймера T1 = CTC сброс при совпадении
(0<<CS12)| (0<<CS11)| (1<<CS10); //предделитель = 1
Чтобы получить частоту 125000, надо прерывания вызывать в 2 раза чаще.... за 2 вызова как раз получим 2 изменения уровня, т.е. один период частоты 125000.
Но с такой частотой на Си скорее всего не будет работать, т.к. прерывания могут просто не успевать выполнятся (ну прям если только в прерывании инвертирование вывода и все, то успеет, а если там еще чего то будет, то нет)
Такую функцию лучше сделать на железной функции таймера, инвертирования вывода порта (там есть несколько выводов, у которых есть такая функция)
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Пн май 27, 2013 00:17:14
Oleg7771
shads писал(а):так попробуй
Код: Выделить всё
OCR1A = 32; //число сравнения для таймера T1 для формирования прерываний с частотой 250000Гц
TIMSK = (1<<OCIE1A); //разрешить прерывание по совпадению T1
TCCR1A =(0<<WGM11)| (0<<WGM10); //режим таймера T1 = CTC сброс при совпадении
TCCR1B =(0<<WGM13)| (1<<WGM12)| //режим таймера T1 = CTC сброс при совпадении
(0<<CS12)| (0<<CS11)| (1<<CS10); //предделитель = 1
Чтобы получить частоту 125000, надо прерывания вызывать в 2 раза чаще.... за 2 вызова как раз получим 2 изменения уровня, т.е. один период частоты 125000.
Но с такой частотой на Си скорее всего не будет работать, т.к. прерывания могут просто не успевать выполнятся (ну прям если только в прерывании инвертирование вывода и все, то успеет, а если там еще чего то будет, то нет)
Такую функцию лучше сделать на железной функции таймера, инвертирования вывода порта (там есть несколько выводов, у которых есть такая функция)
Проверял в Proteus'е у меня получилось 121213 Гц
вот исходник:
.include "tn2313def.inc"
.list
.def tmp = r16
.def _out = r17
.equ _ctc = 32
.cseg
.org 0
main: rjmp res
.org 4
rjmp int_tm1
.org 19
res: ldi tmp,RAMEND
out SPL,tmp
ser tmp
out DDRB,tmp
out PORTB,tmp
ldi tmp,0x09
out TCCR1B,tmp
clr tmp
out TCCR1A,tmp
ldi tmp,high(_ctc)
out OCR1AH,tmp
ldi tmp,low(_ctc)
out OCR1AL,tmp
ldi tmp,0x40
out TIMSK,tmp
ldi tmp,0x80
out ACSR,tmp
sei
ldi _out,1
m1: rjmp m1
int_tm1: ldi r18,1
eor _out,r18
mov r18,_out
out PORTB,_out
reti
дело не в 125кГц, просто я не пойму почему режется частота в 4 раза (8000000/256=31250) а у меня получается 7812
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Пн май 27, 2013 01:03:00
shads
Oleg7771 писал(а):Проверял в Proteus'е у меня получилось 121213 Гц
Все правильно, в регистр сравнения надо грузить не 32, а 31... т.к. счетчик считает от 0 до 31 и того 32....
тогда правильно кажеть 125000
Oleg7771 писал(а):не пойму почему режется частота в 4 раза (8000000/256=31250) а у меня получается 7812
скинь этот код, гляну.
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Пн май 27, 2013 01:11:26
Oleg7771
shads писал(а):Oleg7771 писал(а):Проверял в Proteus'е у меня получилось 121213 Гц
Все правильно, в регистр сравнения надо грузить не 32, а 31... т.к. счетчик считает от 0 до 31 и того 32....
тогда правильно кажеть 125000
Oleg7771 писал(а):не пойму почему режется частота в 4 раза (8000000/256=31250) а у меня получается 7812
скинь этот код, гляну.
исходник тот что я отправлял выше только изменил переменную _cts = 1, и регистр TCCR1B = 0x0C (sts1 + /256)
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Пн май 27, 2013 01:23:52
shads
Oleg7771 писал(а):изменил переменную _cts = 1, и регистр TCCR1B = 0x0C (sts1 + /256)
_ctc = 128-1
уже говорил что задержку надо делать в 2 раза короче чем рассчетная от частоты, т.к. нам надо в прерывании формировать два полупериода
TCCR1B оставь как было 0x09
получается 31250
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Пн май 27, 2013 01:44:14
Oleg7771
shads писал(а):Oleg7771 писал(а):изменил переменную _cts = 1, и регистр TCCR1B = 0x0C (sts1 + /256)
_ctc = 128-1
уже говорил что задержку надо делать в 2 раза короче чем рассчетная от частоты, т.к. нам надо в прерывании формировать два полупериода
TCCR1B оставь как было 0x09
получается 31250
Спасибо, понял, действительно получается четко 31250!
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Вт май 28, 2013 18:23:05
Oleg7771
сделал ещё проще, взял формулу из datasheet и по ней написал программу )
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Вт май 28, 2013 21:13:21
shads
Oleg7771 писал(а):сделал ещё проще, взял формулу из datasheet и по ней написал программу )
Прииииикольно... спасибо.
А мне чет в голову не пришло программку накалякать, хотя мелкие программки для PC тоже ваял.
Я еще проще делал, формулу в EXCEL вставил, тоже не плохо было...
Попробую теперь твоей попользоваться.
PS Ошибочку углядел.....
Там где у тебя окошко OCR1AH написано ORC1AH.....
Ничего.... мож для прикола так и оставить.....
Когда будут обращать внимание на это, говори что это проверка на невнимательность...

Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Вт май 28, 2013 23:04:34
Oleg7771
спасибо что указал на ошибку, я как то не обратил внимания. В EXEL тоже делал, мне показалось что не очень удобно.
Хочу доработать программку чтобы можно было вводить OCR1A и сразу видеть реальную частоту, в этой же программе просто сделаю ещё одно поле для ввода и немного мелких доделок.
Меня ещё один вопрос интересует, хочу сделать регулятор мощности (фазо-импульсный) т.е. чтобы сетевая частота 20мс вызывала внешнее прерывание (синхронизация), и по этому импульсу в обработчике прерывание с помощью ШИМ генерировать импульс определенной ширины (менять угол открытия) на выход для управления симистором.
Только вот не знаю как правильно это синхронизировать?
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Вт май 28, 2013 23:38:28
shads
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Ср май 29, 2013 20:15:31
Oleg7771
по первой ссылке нашел исходник, судя по нику похоже твой) переделал его под CAVR, сразу не компилировался кучу матюков писал) собрал схему, регулирует, но с мерцанием как один полупериод, и почти перед самым максимумом тухнет лампа.
хотел спросить, может быть дело в детекторе нуля? на другом форуме нашел диммер на pic16f629 там в место детектора подается сетевое напряжение через резистор 10М и я так сделал, так же пробовал по схеме
http://forum.easyelectronics.ru/downloa ... =10066&t=1 тоже самое
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Ср май 29, 2013 21:30:59
shads
Твой детектор не выделяет переход через 0, а просто помечает одну полуволну как 0, другую полуволну как 1, поэтому надо ловить изменения на выходе резистора, это и будет переход через 0.
Надо чуть поправить код, вместо этого:
Код: Выделить всё
if (PIN & SINC_LINE){ //анализ синхросигнала
if (! LineState)
LineState = 1;
}
else{
if (LineState){
LineState = 0;
PwmTimer = 0; //переменная PwmTimer обнуляется каждый раз при синхронизации
}
}
напиши так:
Код: Выделить всё
if (PIN & SINC_LINE){ //анализ синхросигнала
if (! LineState){
LineState = 1;
PwmTimer = 0; //переменная PwmTimer обнуляется
}
}
else{
if (LineState){
LineState = 0;
PwmTimer = 0; //переменная PwmTimer обнуляется
}
}
И еще, резистор 10М наверное многовато, при таком большом сопротивлении уже будет сказыватся емкость дорожек, входа контроллера, может переход не правильно ловить.... поставь 1М...
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Ср май 29, 2013 21:59:18
Oleg7771
всё равно мерцает, буду делать детектор нуля ) А на счет того что в крайнем положении ближе к максимуму симистор закрывается, это тоже от этого может быть?
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Ср май 29, 2013 22:09:55
shads
в протеусе есть схемка?
я бы глянул....
и исходник...
там где ты взял код, есть еще файл протеуса, переделай его под свой вариант и покажи тут...
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Ср май 29, 2013 22:33:07
Oleg7771
схема та же и осталась, что была с исходником на сайте. Сделал детектор нуля всё равно мерцает, в чем проблема не пойму в proteus работает правильно. Схема детектора нуля что я собрал (файл zero.jpg) в архиве, также проект proteus и исходник для CAVR.
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Ср май 29, 2013 22:47:06
shads
Изменил в протеусе форму сигнала детектора нуля, раскомментировал новый фрагмент, который выше показал, закомментировал старый...
Все как и положено сейчас....
Сделай просто резистор 1М и не заморачивайся, сейчас я сделал для резистора...
А частота в железе 8МГц? может 1МГц стоит....
А вообще если нужна гальваническая развязка то лучше на оптроне...
Re: помогите разобратся с таймером 1 на tiny2313
Добавлено: Ср май 29, 2013 22:57:56
Oleg7771
извиняюсь, это я протупил, когда ввел твоё изменение забыл скомпилировать зашил тоже самое что было. С исправлением заработало без детектора нуля, через 10М. спасибо за помощь )