|
|
  |
Передача информации с помощью ИК, необходимо передавать 4 команды с одного контроллера на другой |
|
|
|
Mar 20 2011, 15:15
|
Участник

Группа: Участник
Сообщений: 29
Регистрация: 20-03-11
Пользователь №: 63 737

|
Доброго времени суток. Пытаюсь передавать 4 команды от одного контроллера к другому. МК 1 Трансивер Tiny 13, приемник tiny2313. Передать одну команду(внешнее прерывание в тини) не проблема, все работает. А вот никак не могу разобраться с алгоритмом и его реализацией для нескольких команд. Для передатчика использую следующий алгоритм: Если нажата кнопка 1 -передаю 5 раз 20 импульсов с паузой 260мкс после каждого импульса Если нажата кнопка 2 -передаю 10 раз 20 импульсов с паузой 260мкс после каждого импульса ... Если нажата кнопка 4 -передаю 20 раз 20 импульсов с паузой 260мкс после каждого импульса
Приемник должен гонять таймер с частотой самого длинного импульса, в моем случае 26мкс(время 1 импульса)*20(кол-во пульсаций)*20(раз передается импульс)+260мкс(задержка после каждой пачки импульсов)*20(пачек импульсов)=15,6 мс. Что равно 64 Гц (если я не ошибаюсь).
В момент когда нажата кнопка на передатчике, на приемнике срабатывает внешнее прерывание
interrupt [EXT_INT0] void ext_int0_isr(void) { TCNT0=0xF0; //запускаем таймер 64 Гц, время самого длинного импульса TCCR0B=0x04;
}
И в этот момент мне нужно посчитать сколько же было послано пачек 5,10, 15, или 20. Как не знаю. Застрял. Помогите. Может быть есть стандартные библиотеки для МК на этот случай. Пишу в CVAVR
|
|
|
|
|
Mar 20 2011, 16:05
|
Гуру
     
Группа: Свой
Сообщений: 5 273
Регистрация: 30-03-10
Пользователь №: 56 295

|
Цитата(eugmai86 @ Mar 20 2011, 18:15)  И в этот момент мне нужно посчитать сколько же было послано пачек 5,10, 15, или 20. Как не знаю. Застрял. Помогите. Может быть есть стандартные библиотеки для МК на этот случай. Пишу в CVAVR Очень просто. Цифровой автомат. Состояние S0: приемник ждет прерывания. При получении прерывания приемник переходит в S1 Состояние S1: приемник принимает импульсы (первые пять). При получении первых 5-ти импульсов, если через заданное время больше импульсов принято не было, то приемник считает, что это команда из пяти импульсов и переходит в S0. Если же импульсы были, то приемник переходит в S2. Состояние S2: приемник принимает импульсы (очередные пять). При получении очередных 5-ти импульсов, если через заданное время больше импульсов принято не было, то приемник считает, что это команда из десяти импульсов и переходит в S0. Если же импульсы были, то приемник переходит в S3. И так далее. Но так делать не надо. Почему бы просто не передавать команды по UART, защищая каждую команду (например, такую: "CMD1", "CMD2", ...) байтом CRC8 (или словом CRC16, или CRC32) ? Просто, стандартно, длина команды всегда постоянна, легко добавлять новые команды, реализаций CRC готовых масса ...
Сообщение отредактировал kovigor - Mar 20 2011, 16:07
|
|
|
|
|
Mar 20 2011, 16:40
|
Участник

Группа: Участник
Сообщений: 29
Регистрация: 20-03-11
Пользователь №: 63 737

|
Дело в том, что у тини 13 нет UART
Т.е. если есть внешнее прерывание вызывается ф-ция обработки, она же считает сколько было изменений на ноге контроллера. А как правильно таймер запустить чтоб он стартовал с начала сигнала и останавливался по переполнению, а не стартовал при каждом прерывании как у меня. Только не отправляйте в даташит, читал много раз и внимательно. Просто некому один раз в живую объяснить. Спасибо char tick=0; interrupt [EXT_INT0] void ext_int0_isr(void) { TCNT0=0xF0; //запускаем таймер 64 Гц, время самого длинного импульса TCCR0B=0x04; tick++; } void tick_calc (void) { if (0<<=5) { //do smth1 TCNT0=0x00; //останавливаю таймер TCCR0B=0x00; tick=0;//сбрасываю тики } ... if (15<tick<=20) { //do smth4 TCNT0=0x00; //останавливаю таймер TCCR0B=0x00; tick=0; } }
|
|
|
|
|
Mar 20 2011, 16:49
|
Участник

Группа: Участник
Сообщений: 29
Регистрация: 20-03-11
Пользователь №: 63 737

|
На Tiny2313 включено внешнее прерывание на INT0, на эту ногу повешен выход TSOP4838
|
|
|
|
|
Mar 20 2011, 17:01
|
Участник

Группа: Участник
Сообщений: 57
Регистрация: 31-10-10
Пользователь №: 60 558

|
ИК-сигнал не очень стабильная среда передачи информации. Вы уверенны, что вам не требуется подтверждения приёма команд со стороны приёмника? Ну и может стоит обратить внимание на "старые" проверенные протоколы для ПДУ бытовой техники или расширить их введя избыточность данных.
|
|
|
|
|
Mar 20 2011, 17:07
|
Участник

Группа: Участник
Сообщений: 29
Регистрация: 20-03-11
Пользователь №: 63 737

|
IRDA.zip ( 4.77 килобайт )
Кол-во скачиваний: 106На данном этапе обратная связь не требуется, смотрел образцы для NEC и Sony(см приложение). Так и не смог разобраться. Опыта маловато.
|
|
|
|
|
Mar 20 2011, 18:35
|
Участник

Группа: Участник
Сообщений: 29
Регистрация: 20-03-11
Пользователь №: 63 737

|
main.zip ( 1.46 килобайт )
Кол-во скачиваний: 124Смотрите в приложении. Или часть кода тут: #define IR_LED PORTB.0 volatile bit button_pressed1, button_pressed2, button_pressed3, button_pressed4; //флаг void press_key (void) { char i; for(i=0;i<=19;i++)//пачка из 30 импульсов { delay_us(13);// почти меандр 38кГц IR_LED=1; delay_us(13); IR_LED=0; }; delay_us(260);//та самая пауза, }; Дальше в main: if (PINB.1 == 0 && button_pressed1 == 0) //Если нажата кнопка 1 { char k; for (k=0;k<5;k++) { press_key(); }; button_pressed1 = 1; } ... if (PINB.4 == 0 && button_pressed4 == 0) //Если нажата кнопка 4 { char k; for (k=0;k<20;k++) { press_key(); }; button_pressed4 = 1; } if (PINB.4 == 1) button_pressed4 = 0; //сбрасываем флаг Получается я передаю 30 импульсов а за ними пауза.
|
|
|
|
|
Mar 20 2011, 19:39
|
Знающий
   
Группа: Свой
Сообщений: 812
Регистрация: 22-01-05
Из: SPb
Пользователь №: 2 119

|
Цитата(eugmai86 @ Mar 20 2011, 21:35)  Получается я передаю 30 импульсов а за ними пауза. Ну значит в этом месте все правильно. Только паузу между пачками лучше побольше раза в два-три. Я бы посоветовал кодировать кнопки интервалами между пачками.
|
|
|
|
|
Mar 20 2011, 20:22
|
Участник

Группа: Участник
Сообщений: 29
Регистрация: 20-03-11
Пользователь №: 63 737

|
Так всеже как правильно таймер запустить чтоб он стартовал с начала сигнала и останавливался по переполнению, а не стартовал при каждом прерывании. Вопрос то по сути не сложный, недавно програмирую, мало что знаю поэтому и спрашиваю. Нужно при появлении низкого уровня (внешнее прерывание) посчитать кол-во импульсов. Какие импульсы, их длины все написал, подскажите как. Я знаю что есть RC-5 RC-6 еще вагон протоколов, но ведь требуется передать 4 (четыре) команды а не 20.
|
|
|
|
|
Mar 20 2011, 20:45
|
Знающий
   
Группа: Свой
Сообщений: 812
Регистрация: 22-01-05
Из: SPb
Пользователь №: 2 119

|
Цитата(eugmai86 @ Mar 20 2011, 23:22)  Так всеже как правильно таймер запустить чтоб он стартовал с начала сигнала и останавливался по переполнению, а не стартовал при каждом прерывании. Вопрос то по сути не сложный, недавно програмирую, мало что знаю поэтому и спрашиваю. Нужно при появлении низкого уровня (внешнее прерывание) посчитать кол-во импульсов. Какие импульсы, их длины все написал, подскажите как. Я знаю что есть RC-5 RC-6 еще вагон протоколов, но ведь требуется передать 4 (четыре) команды а не 20. Не морочьте себе голову с протоколами. В вашем описании немного сбивает с толку, что вы называете импульсами и короткие импульсы на выходе ИК-передатчика и сигналы на выходе ИК-приемника. У приемника на выходе уже имульсы, примерно совпадающие с длительностью пачки из 30коротких импульсов. Теперь относительно измерения интервала времени между пачками. (Это я предполагаю, что вы вняли моему предложению кодировать кнопки интервалами между пачками.) При поступлении пачки у вас происходит прерывание. Вы должны в подпрограмме обработки перерывания проверить состояние таймера, который заполняется импульсами от основного ТГ контроллера (через прескалер, если он там есть - точно не помню). Тут времянку надо аккуратно посчитать, чтобы таймер не переполнялся при самом большом интервале меду пачками. Дальше, вы посмотрели на содержимое таймера и решили, какая кнопка нажата. После этого вы обнуляете таймер и выходите из прерывания. До прихода следующей пачки. Для пущей надежности окончательное решение о нажатой кнопке можно принимать, когда накопилось три (или пять) одинаковых решений относительно кнопки (я предполагаю, что пачек за время нажатия кнопки уйдет не менее 5-ти). Как-то так. А с вашей программой вряд ли кто будет подробно разбираться. Ну, если у кого совсем много свободного времени.
|
|
|
|
|
Mar 20 2011, 20:55
|
Участник

Группа: Участник
Сообщений: 29
Регистрация: 20-03-11
Пользователь №: 63 737

|
ясно, спасибо. тут еще порекомендовали попробовать без таймера. просто считать сколько прерывание случилось. разбираюсь. спасибо
|
|
|
|
|
  |
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|