обработка импульсов микроконтроллером

Вопросы настройки, программирования, прошивки микроконтроллеров и микросхем программируемой логики
DOCKtor_vatson
Родился
Сообщения: 10
Зарегистрирован: Пн дек 10, 2007 01:42:52
Контактная информация:

обработка импульсов микроконтроллером

Сообщение DOCKtor_vatson »

Здравствуйте. Не могу решить одну проблему с обработкой импульсов микроконтроллером.
1. Есть необходимость обрабатывать импульс с приёмника радиоаппаратуры. С приёмника, в зависимости от положения ручек управления на передатчике, на один канал приходит импульс от 0.8 мс до 2.2 мс. Можно ли с помощью кода программы как то преобразоваться это изменение импульсов до логического 0 или 1, т.е. при подаче импульса от 0.8 до 1мс считать 0, а при 1.8 до 2.2 мс -1?
2. Если этого сделать нельзя программно, как реализовать с помощью постоянной логики?
Аватара пользователя
Meteor
Друг Кота
Сообщения: 3961
Зарегистрирован: Пн июл 13, 2009 14:37:39
Откуда: Московская область, наукоград.....
Контактная информация:

Сообщение Meteor »

Можно решить на контроллере например AVR используя два внешних прерывания. Одно запускает старт счетчика по переднему фронту, а второе обрабатывает задний фронт и ищет разницу во времени. Для логики, если импульс идет с периодом, то можно настроить интегрирующую цепочку, с постоянной времени такой чтоб при одной длительности она не заряжалась, а при другой зараяжалась (проходила порог срабатывания). какой путь ыбирать Вам решать
Загружая на вход компьютера "мусор", на выходе получим "мусор^32".
PS. Не работаю с: Proteus, Multisim, EWB, Micro-Cap... не спрашивайте даже
DOCKtor_vatson
Родился
Сообщения: 10
Зарегистрирован: Пн дек 10, 2007 01:42:52
Контактная информация:

Сообщение DOCKtor_vatson »

А нельзя ли сделать проще?
например:
сигнал пустить на один из портов d.
в прошивке назначить опрос порта с задержкой в эти самые 0.8 мс и повторить опрос, если сигнала повторно нет, то засчитать как 0, если сигнал повторно есть то считать как 1, а дальше не сложно.
Аватара пользователя
BCluster
Собутыльник Кота
Сообщения: 2512
Зарегистрирован: Пн апр 06, 2009 19:33:29
Откуда: Молдова, Кишинев
Контактная информация:

Сообщение BCluster »

Можно - не эффективно, но можно (:
akl
Друг Кота
Сообщения: 4444
Зарегистрирован: Пт мар 07, 2008 06:54:43
Откуда: Ижевск

Re: обработка импульсов микроконтроллером

Сообщение akl »

DOCKtor_vatson писал(а):... приходит импульс от 0.8 мс до 2.2 мс. Можно ли с помощью кода программы как то преобразоваться это изменение импульсов до логического 0 или 1, т.е. при подаче импульса от 0.8 до 1мс считать 0, а при 1.8 до 2.2 мс -1?...

Здравствуйте. Какой логический уровень будет соответствовать сигналу длительностью 1.4мс?
Аватара пользователя
Neekeetos
Держит паяльник хвостом
Сообщения: 993
Зарегистрирован: Пн сен 18, 2006 11:16:05
Откуда: Тула
Контактная информация:

Re: обработка импульсов микроконтроллером

Сообщение Neekeetos »

DOCKtor_vatson писал(а):Здравствуйте. Не могу решить одну проблему с обработкой импульсов микроконтроллером.
1. Есть необходимость обрабатывать импульс с приёмника радиоаппаратуры. С приёмника, в зависимости от положения ручек управления на передатчике, на один канал приходит импульс от 0.8 мс до 2.2 мс. Можно ли с помощью кода программы как то преобразоваться это изменение импульсов до логического 0 или 1, т.е. при подаче импульса от 0.8 до 1мс считать 0, а при 1.8 до 2.2 мс -1?
2. Если этого сделать нельзя программно, как реализовать с помощью постоянной логики?


Это элементарно, ватсон. Надо организовать в МК прерывание с частотой 5000Гц и в нем считывать состояние входа. Тогда в силу того что период опроса равен 0,2мс будет следующее - при получении 4 и 5 единиц подряд считаем 0, если от 9 до 11 единиц подряд то считаем 1, если вне диапазонов то считаем не подходит.
DOCKtor_vatson
Родился
Сообщения: 10
Зарегистрирован: Пн дек 10, 2007 01:42:52
Контактная информация:

Re: обработка импульсов микроконтроллером

Сообщение DOCKtor_vatson »

akl писал(а):
DOCKtor_vatson писал(а):... приходит импульс от 0.8 мс до 2.2 мс. Можно ли с помощью кода программы как то преобразоваться это изменение импульсов до логического 0 или 1, т.е. при подаче импульса от 0.8 до 1мс считать 0, а при 1.8 до 2.2 мс -1?...

Здравствуйте. Какой логический уровень будет соответствовать сигналу длительностью 1.4мс?



я разделил например.. можно разделить как угодно хоть от 0.8 до 1.4 =0, а от 1.5 до 2.2 =1
DOCKtor_vatson
Родился
Сообщения: 10
Зарегистрирован: Пн дек 10, 2007 01:42:52
Контактная информация:

Re: обработка импульсов микроконтроллером

Сообщение DOCKtor_vatson »

Neekeetos писал(а):Это элементарно, ватсон. Надо организовать в МК прерывание с частотой 5000Гц и в нем считывать состояние входа. Тогда в силу того что период опроса равен 0,2мс будет следующее - при получении 4 и 5 единиц подряд считаем 0, если от 9 до 11 единиц подряд то считаем 1, если вне диапазонов то считаем не подходит.


я так думаю этот вариант не подходит, почему, будет видно на осциллограммах. Постараюсь выложить вечером.
AndryG
Открыл глаза
Сообщения: 76
Зарегистрирован: Сб ноя 10, 2007 14:28:04
Откуда: UA
Контактная информация:

Сообщение AndryG »

Meteor писал(а):Можно решить на контроллере например AVR используя два внешних прерывания...

Можно обойтись одним внешним прерыванием и таймером.
Внешнее прерывание настраиваем на любой фронт.

Внутри прерывания:
если начало импульса - стартуем таймер.
если конец - останавливаем таймер и смотрим, что он там насчитал.
Аватара пользователя
Meteor
Друг Кота
Сообщения: 3961
Зарегистрирован: Пн июл 13, 2009 14:37:39
Откуда: Московская область, наукоград.....
Контактная информация:

Сообщение Meteor »

AndryG писал(а):Можно обойтись одним внешним прерыванием и таймером.
Внешнее прерывание настраиваем на любой фронт.
Внутри прерывания:
если начало импульса - стартуем таймер.
если конец - останавливаем таймер и смотрим, что он там насчитал.

Можно, но мне такие решения не нравятся, прежде всего тем что надо пересраивать режимы работы. Причем изменять внутри самого прерывания. Кстати тут подобная тема бродила, и не одна. Вот например: http://radiokot.ru/forum/viewtopic.php?t=19002
Выводы:
1) Фсйо уже изобретено до нас; :wink:
2) Иногда надо пользоватьсйа поиском... :tea:
Загружая на вход компьютера "мусор", на выходе получим "мусор^32".
PS. Не работаю с: Proteus, Multisim, EWB, Micro-Cap... не спрашивайте даже
Аватара пользователя
OBIVAN
Встал на лапы
Сообщения: 84
Зарегистрирован: Вт ноя 25, 2008 18:56:41

Сообщение OBIVAN »

Я так понимаю речь идет о пропорциональном управлении, исходя из слов передатчик точно выдает пропорциональные сигналы, самое простое решение на мой взгляд: 1- делаем предсенхронизацию по любому выводу МК. то-есть ищем фронт сигнала, 2-запускаем таймер от внутреннего источника тактовых импульсов, 3- ждем изменения фронта и останавливаем таймер, 4-зная какой частотой мы заполняли таймер подсчитываем длительность и принимаем решение 1 или ноль или что там еще понадобится,в принципе туда команд можно будет всунуть поболее чем 2.
Аватара пользователя
Meteor
Друг Кота
Сообщения: 3961
Зарегистрирован: Пн июл 13, 2009 14:37:39
Откуда: Московская область, наукоград.....
Контактная информация:

Сообщение Meteor »

OBIVAN писал(а):Я так понимаю ...самое простое решение на мой взгляд: 1- делаем предсенхронизацию по любому выводу МК. то-есть ищем фронт сигнала, 2-запускаем таймер от внутреннего источника тактовых импульсов, 3- ждем изменения фронта и останавливаем таймер, 4-зная какой частотой мы заполняли таймер подсчитываем длительность и принимаем решение

Если других функций нет у МК то да. А если есть то проще освоить прерывания. По ссылкам найдете решения. Зачем изобретать лисапед, когда достаточно поднапрячься и сделать как надо.. :tea:
Загружая на вход компьютера "мусор", на выходе получим "мусор^32".
PS. Не работаю с: Proteus, Multisim, EWB, Micro-Cap... не спрашивайте даже
DOCKtor_vatson
Родился
Сообщения: 10
Зарегистрирован: Пн дек 10, 2007 01:42:52
Контактная информация:

Сообщение DOCKtor_vatson »

выкладываю осциллограммы. огромное спасибо вам за советы, сегодня буду пробовать программить. Уважаемый Meteor, посмотрел то, что вы посоветовали, к сожалению не понимаю язык си, работаю, точнее изучаю, асамблер.
Вложения
143304.jpg
Развёртка 5 мс. получается, что частота повторений импульса 20-22мс
(64.65 КБ) 648 скачиваний
143420.jpg
развёртка 0.2, получается что при нижнем положении ручки управления длинна импульса составляет 0.8 мс
(61.76 КБ) 677 скачиваний
143343.jpg
развёртка 0.2, при верхнем положении ручки, длинна импульса составляет 1.8 (т.е. крайнее значение)
(62.54 КБ) 393 скачивания
Аватара пользователя
Meteor
Друг Кота
Сообщения: 3961
Зарегистрирован: Пн июл 13, 2009 14:37:39
Откуда: Московская область, наукоград.....
Контактная информация:

Сообщение Meteor »

DOCKtor_vatson писал(а):посмотрел то, что вы посоветовали, к сожалению не понимаю язык си, работаю, точнее изучаю, асамблер.

Я ссылался на идею, а не текст. Сам тоже пишу на ассемблере причем уже с 3 архитектурой. Доволен как кот у сметаны:)))
Загружая на вход компьютера "мусор", на выходе получим "мусор^32".
PS. Не работаю с: Proteus, Multisim, EWB, Micro-Cap... не спрашивайте даже
DOCKtor_vatson
Родился
Сообщения: 10
Зарегистрирован: Пн дек 10, 2007 01:42:52
Контактная информация:

Сообщение DOCKtor_vatson »

добрый вечер. уже несколько дней пишу программу. Первые пробы дали отрицательный результат, так как взялся сразу за сложное.
столкнулся с проблемой такого рода. когда проиходит обработка тела программы (на разные порты подаются импульсы), допустим срабатывает прерывание, происходит обработка прерывания при котором считывается порт D и передаётся на PB1. после этого на выход PB1 в зависимости от полученного результата с порта D подаётся 1 или 0. на как только прерывание заканчивается, основная программа сбрасывает это значение и сигнал перестаёт поступать до нового прерывания. как сделать так чтоб получаившейся в конце когда прерывания результат сохранялся и работал в теле программы.

Код: Выделить всё

.include "c:\avr\avrasm\appnotes\tn2313def.inc"

.def     Temp=R16
.def     Temp1=R17
.def     Temp2=R18
.def     Temp3=R19
.def     Temp4=R20
.cseg
.org 0

rjmp Reset            ;вектора прерываний
rjmp INT_0
rjmp INT_1
rjmp Timer1_capt1
rjmp Timer1_comp1
rjmp Timer1_OVF1
rjmp Timer0_OVF0
rjmp UART_RX
rjmp UART_UDRE
rjmp UART_TX
rjmp ANA_COMP




;Reset:
;INT_0:
INT_1:
Timer1_capt1:
Timer1_comp1:
Timer1_OVF1:
Timer0_OVF0:
UART_RX:
UART_UDRE:
UART_TX:
ANA_COMP:
.org 20            //размещение тела программы
Reset:            //тело программы
          ldi Temp,RamEnd       //инициализация стека
          out SPL,Temp


            // настройка прерывания int0
   ldi Temp,0b00000000   
   out DDRD,Temp      //порт D настроен на вход


          ldi Temp,0b11111111   //настройка портов
          out DDRB,Temp
   out  PORTD,temp
   ldi Temp,0b00000011   // по фронту
   out MCUCR,Temp      //установка триггера
   ldi Temp,0b01000000   
   out GIMSK,Temp      
   ldi Temp,0b01100000
   out GIFR,Temp      //сброс флагов прерываний
   sei         //разрешение прерывания int0
        // конец настройки прерывания int0   


Begin:    ldi Temp,0b11010000   
          rcall mig1           

          ldi Temp,0b11000000   
          rcall mig1           
          ldi Temp,0b11010000   
          rcall mig1           
         
          ldi Temp,0b11000000   
          rcall mig2           

          ldi Temp,0b11100000 
          rcall mig1           

          ldi Temp,0b11000000   
          rcall mig1           

          ldi Temp,0b11100000   
          rcall mig1           


          ldi Temp,0b11000000   
          rcall mig2           

     sei

          rjmp Begin           

;****************************************************
;Задержка

mig1:    out PortB,Temp        ;вывод на индикацию

          ldi Temp1,0
          ldi Temp2,70
          ldi Temp3,1

Loop:     dec Temp1
          brne Loop

          dec Temp2
          brne Loop

          dec Temp3
          brne Loop

          ret

mig2:    out PortB,Temp       ;вывод на индикацию

          ldi Temp1,0
          ldi Temp2,0
          ldi Temp3,5

Loop2:     dec Temp1
          brne Loop2

          dec Temp2
          brne Loop2

          dec Temp3
          brne Loop2

          ret

mig:      ldi  Temp1,0
          ldi  Temp2,70

wt1:      dec  Temp1
          brne wt1

     dec  Temp2
          brne wt1

          ret

int_0:
;*****************************************
;размещение обработчика прерывания int0
   in   temp,PINB
   sbrc temp,0
   rjmp m1
   sbi  PORTB,0
   rjmp m2
m1:   cbi  PORTB,0
   
m2:   reti

akl
Друг Кота
Сообщения: 4444
Зарегистрирован: Пт мар 07, 2008 06:54:43
Откуда: Ижевск

Сообщение akl »

Здравствуйте. Программа, после выполнения прерывания и окончания текущей задержки, командой

Код: Выделить всё

ldi Temp,0bxxxxxxx0

принудительно сбрасывает значение PORTB0.
Сделал так, вроде получилось.
Аватара пользователя
SeamaNCOS
Встал на лапы
Сообщения: 107
Зарегистрирован: Ср дек 10, 2008 15:10:59
Откуда: KPACHO9PCK
Контактная информация:

Сообщение SeamaNCOS »

Можно задействовать Timer1_comp1
настроить
Reset:
out TIMSK,Temp ;разрешить прерывание компаратора
out TCCR1B,Temp ;тактовый сигнал
;инициализация компаратора настраиваем на прерывание 1.79мс
out OCR1AH,Temp
out OCR1AL,Temp
out MCUCR,Temp ;НАСТРОИТЬ INT_0 ПО ВОЗРАСТАЮЩЕМУ ФРОНТУ

в прерывании
INT_0:
ldi Temp,0b01000000;разрешить прерывание компаратора
out TIMSK,Temp

ldi Temp,0 ;обнуление таймера
out TCNT1H,Temp
out TCNT1L,Temp
reti

в прерывании
Timer1_comp1:
ldi Temp,0b00000000 ;запретить прерывание компаратора
out TIMSK,Temp

in temp,PIND ;читаем PD2(int0)
ori temp,0b11111011 ;обрезка по маске
cpi temp,0b11111111 ;сравнение
breq taim18 ;если равно перейти
ldi temp1,0
reti

taim18:
ldi temp1,1
reti

Inf: ;бесконечный цикл
OUT PORTB,temp1
rjmp Inf

ВОТ КАК ТО ТАК
Чем больше думаеш, тем дольше уснуть не можеш...
Аватара пользователя
Dock
Первый раз сказал Мяу!
Сообщения: 37
Зарегистрирован: Сб дек 22, 2007 17:13:24
Контактная информация:

Сообщение Dock »

akl писал(а):Здравствуйте. Программа, после выполнения прерывания и окончания текущей задержки, командой

Код: Выделить всё

ldi Temp,0bxxxxxxx0

принудительно сбрасывает значение PORTB0.
Сделал так, вроде получилось.


попробовал ваш код, у меня некорректно обрабатывает тело программы (сначало подаётся разовый сигнал на PB5 потом на PB6 и впоследствии горят 4 светика и ничего не происходит, прерывание работает). может фузы какие не включены. кристал tini 2313 20 su

а нельзя как то прибавить дорпустим значения temp к temp1.
после прерывания сохранить значения в temp а в начале каждого вывода в порт просто складывать значения??

и здесь решение найдено
команда add
получается после прерывания
in temp4, pinb ;сохраняем значение после прерывания

в теле программы
add temp,temp4 сложение значений
out portb,temp вывод на индикацию
Последний раз редактировалось Dock Пт ноя 06, 2009 20:09:18, всего редактировалось 1 раз.
Аватара пользователя
Dock
Первый раз сказал Мяу!
Сообщения: 37
Зарегистрирован: Сб дек 22, 2007 17:13:24
Контактная информация:

Сообщение Dock »

решение найдено
применив вместо этого:
Ldi temp, 0x0xxxxxxx
out portb,temp

вот это:

sbi port,x
и
cbi port,x

кому интересно могу выложить прошивку.
akl
Друг Кота
Сообщения: 4444
Зарегистрирован: Пт мар 07, 2008 06:54:43
Откуда: Ижевск

Сообщение akl »

Пока писал решение было найдено.
Закрыто

Вернуться в «Микроконтроллеры и ПЛИС»