Объединение самодельного дальномера и микроконтроллера

July 6, 2014 by admin Комментировать »

Первое, что может мешать этому – отсутствие в составе микросхемы встроенного аналого- цифрового преобразователя Если у робота, где используется микроконтроллер PIC16F887, измеритель расстояния работает в паре с АЦП, то что делать нам

Да, модуля АЦП нет, но есть встроенные компараторы, и есть программно управляемое опорное напряжение Если определить это опорное напряжение равным 100 мВ, что соответствует расстоянию до отражающей поверхности более 15 см, то при превышении напряжения сигнала от фотоприёмника, мы будем «бить тревогу»

Как и прежде, опишем цель нашей следующей работы:

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

2         Микроконтроллер будет постоянно излучать ИК-сигнал, но при напряжении на входе компаратора больше 100 мв, когда компаратор переключается, должен устанавливаться флаг – справа препятствие

3         При запросе по USART от основного контроллера, когда робот обнаруживает препятствие перед собой, микроконтроллер PIC16F628A должен отправить состояние флага: «0» – справа препятствия нет, «1» – справа препятствие

В сущности, описав выше, что мы намерены получить в результате, мы разбили задачу на подзадачи, и готовы приступить к работе, используя в качестве плана работы наше описание

Что можно найти в описании контроллера об опорном напряжении и компараторах Поищем

Модуль компараторов позволяет использовать внутренний источник опорного напряжения, описанный в разделе 110 Сигнал внутреннего источника опорного напряжения подключается к выводам VIN+ обоих компараторов, когда биты конфигурации CM<2:0>=010 (см рисунок 9-1)

Посмотрим рисунок:

Рис 5313 Рисунок из справки – схема включения компараторов

Обратимся к описанию регистра, упомянутого выше:

Рис 5314 Регистр CMCON микроконтроллера PIC16F628A Бит 7: C2OUT: Выход компаратора 2

Если C2INV=0

1 = C2 VIN+ > C2 VIN-

0 = C2 VIN+ < C2 VIN-

Если C2INV=1

0 = C2 VIN+ > C2 VIN-

1 = C2 VIN+ < C2 VIN-

Бит 6: C1OUT: Выход компаратора 1 Если C1INV=0

1 = C1 VIN+ > C1 VIN-

0 = C1 VIN+ < C1 VIN-

Если C1INV=1

0 = C1 VIN+ > C1 VIN-

1 = C1 VIN+ < C1 VIN-

Бит 5: C2INV: Инверсный выход компаратора 2 1 = C2 инверсный выход

0 = C2 не инверсный выход

Бит 4: C1INV: Инверсный выход компаратора 1 1 = C1 инверсный выход

0 = C1 не инверсный выход

Бит 3: CIS: Подключение входов компараторов Если CM2:CM0 = 001

1 = C1 VIN- подключен к RA3 0 = C1 VIN- подключен к RA0 Если CM2:CM0 = 010

1 = C1 VIN- подключен к RA3 C2 VIN- подключен к RA2

0 = C1 VIN- подключен к RA0 C2 VIN- подключен к RA1

Биты 2-0: CM2:CM0: Режим работы компараторов Смотрите рисунок выше

И в завершение заглянем в раздел 11:

Настройка источника опорного напряжения

Источник опорного  напряжения  может иметь 16 различных  уровней  напряжения  для каждого диапазона

Уравнение вычисления напряжения:

Если VRR = 1: VREF = (VR<3:0>/24) x VDD

Если VRR = 0: VREF = (VDD x ¼) + (VR<3:0>/32) x VDD

Время установки напряжения должно определяться по напряжению на выводе VREF

И вот описание регистра настройки опорного напряжения:

Рис 5315 Регистр VRCON

Бит 7: VREN: Включение источника опорного напряжения 1 = источник опорного напряжения включен

0 = источник опорного напряжения выключен и не потребляет тока Бит 6: VROE: Включение выхода VREF

1 = выход VREF подключен к RA2

0 = выход VREF не подключен к RA2

Бит 5: VRR: Диапазон выходного напряжения VREF 1 = нижний диапазон

0 = верхний диапазон

Бит 4: Не используется: читается как ‘0’

Биты 3-0: VR3:VR0: Выбор выходного напряжения VREF 0 <= VR[3:0] <= 15 Если VRR = 1: VREF = (VR<3:0>/24) x VDD

Если VRR = 0: VREF = (VDD x ¼) + (VR<3:0>/32) x VDD

И ещё одно замечание из datasheet:

Соответствующие  биты  в  регистре  TRISA  определяют  подключать  или  нет  выход компараторов к выводам RA3 и RA4/T0CKI (если CM<2:0> = 110 или 001)

Чтобы написать эту часть программы, двинемся в обратном направлении Вначале определим, как получить опорное напряжение порядка 100 мВ

Запишем в регистр VRCON число 11100001 (0xE1) Запишем в CMCON число 11000110 (0xC6) Что отвечает настройке несколько отличающейся от рекомендаций, но работающей в программе:

void main() { VRCON = 0xE1 CMCON = 0xC6 TRISA = 0xF7

while(1)

}

Рис 5316 Работа компаратора с опорным напряжением

Пороговое напряжение, правда, не 100 мВ, но чуть больше 200 мВ (что вытекает из возможностей встроенного опорного напряжения)

Соединив выход компаратора с входом микроконтроллера, который мы можем опрашивать, мы получим следующее развитие программы:

void main() { VRCON = 0xE1 CMCON = 0xC6 TRISA = 0xF3

while(1)

{

if (PORTBF0 == 1) PORTAF2 = 1 else PORTAF2 = 0

}

}

Установка вывода RA2 в единицу или сброс в ноль нужны в качестве проверки:

Рис 5317 Промежуточная проверка

Теперь мы заменим эту проверочную операцию операцией управления флагом

char flag = 0 void main() {

VRCON = 0xE1 CMCON = 0xC6 TRISA = 0xF3

while(1)

{

if (PORTBF0 == 1) flag = 0

else flag = 1

}

}

И добавим в программу прерывание по UART Заведуют прерываниями регистр INTCON:

Рис 5318 Биты регистра INTCON

Бит 7: GIE: Глобальное разрешение прерываний

1 = разрешены все немаскированные прерывания 0 = все прерывания запрещены

Бит 6: PEIE: Разрешение прерываний от периферийных модулей

1 = разрешены все немаскированные прерывания периферийных модулей 0 = прерывания от периферийных модулей запрещены

Бит 5: T0IE: Разрешение прерывания по переполнению TMR0 1 = прерывание разрешено

0 = прерывание запрещено

Бит 4: INTE: Разрешение внешнего прерывания INT 1 = прерывание разрешено

0 = прерывание запрещено

Бит 3: RBIE: Разрешение прерывания по изменению сигнала на входах RB7:RB4 PORTB 1 = прерывание разрешено

0 = прерывание запрещено

Бит 2: T0IF: Флаг прерывания по переполнению TMR0

1 = произошло переполнение TMR0 (сбрасывается программно) 0 = переполнения TMR0 не было

Бит 1: INTF: Флаг внешнего прерывания INT

1*) = выполнено условие внешнего прерывания на выводе RB0/INT 0 = внешнего прерывания не было

Бит 0: RBIF: Флаг прерывания по изменению уровня сигнала на входах RB4:RB7 PORTB 1*) = зафиксировано изменение уровня сигнала на одном из входов RB7:RB4

0 = не было изменения уровня сигнала ни на одном из входов RB7:RB4

*) сбрасывается программно И регистр PIE1:

Рис 5319 Биты регистра PIE1

Бит 7: EEIE: Разрешение прерывания по окончанию записи в EEPROM данных 1 = прерывание разрешено

0 = прерывание запрещено

Бит 6: CMIE: Разрешение прерывания от компараторов 1 = прерывание разрешено

0 = прерывание запрещено

Бит 5: RCIE: Разрешение прерывания от приемника USART 1 = прерывание разрешено

0 = прерывание запрещено

Бит 4: TXIE: Разрешение прерывания от передатчика USART 1 = прерывание разрешено

0 = прерывание запрещено Бит 3: Не реализован: читается как 0

Бит 2: CCP1IE: Разрешение прерывания от модуля CCP1 1 = прерывание разрешено

0 = прерывание запрещено

Бит 1: TMR2IE: Разрешение прерывания по переполнению TMR2 1 = прерывание разрешено

0 = прерывание запрещено

Бит 0: TMR1IE: Разрешение прерывания по переполнению TMR1 1 = прерывание разрешено

0 = прерывание запрещено

Допишем разрешения прерывания и программу обработки прерывания

char flag = 0 char cmnd = 0

void interrupt() {

if (UART1_Data_Ready() == 1) { cmnd = UART1_Read()

}

if (flag == 1) UART1_Write(1) else UART1_Write(0)

INTCONPEIE = 1

}

void main() {

TRISA = 0xF3 INTCONGIE = 1

INTCONPEIE = 1

PIE1RCIE = 1 VRCON = 0xE1 CMCON = 0xC6 UART1_Init(4800)

Delay_ms(100) while(1)

{

if (PORTBF0 == 1) flag = 0

else flag = 1

}

}

Промоделируем ситуацию за компьютером:

Рис 5320 Моделирование работы второго микроконтроллера

Я никак не определял команду запроса к контроллеру, поэтому можно отправлять любой символ Но, если потребуется, скажем, несколько команд, то для каждой можно определить свой символ или набор символов Первый отклик после команды был выполнен при напряжении на выходе детектора более 200 мВ, второй, как показано на рисунке

Осталось проверить работу двух микроконтроллеров, заменив виртуальный терминал контроллером PIC16F887 Я не буду писать для него полную программу Сейчас мне это не важно Я напишу программу, в которой каждую секунду будет отправляться команда, запрашивающая состояние флага, определяемого датчиком второго микроконтроллера Вот эта программа:

void main() { UART1_Init(4800)

while (1) { UART1_Write(a) Delay_ms(1000)

}

}

Программу легко проверить за компьютером:

Рис 5321 Проверка программы отправки запроса

И  пришло  время  соединить  два  микроконтроллера,  чтобы  промоделировать  их  совместную работу

Рис 5322 Моделирование совместной работы двух микроконтроллеров

Изначально я хотел водрузить самодельный дальномер на платформу робота, но по некоторому размышлению решил, что для меня это  только дополнительные механические работы, а вам будет интереснее самостоятельно проверить всё с реальным макетированием

Конечно, было бы ещё интереснее снабдить робота, скажем, сервоприводом, на платформе которого укрепить дополнительный датчик, что позволило бы роботу «обозревать» окрестности с большим успехом

Вероятно, фабричный датчик расстояния работает лучше, но самодельный, согласитесь, дешевле Но и не это главное Главное, проводя эксперименты, вы лучше поняли, как работают такие датчики, как можно самостоятельно поставить задачу и решить её, следуя плану, который вы сами написали, сами же и выполнили

Одно замечание: если вас не устраивает напряжение в 200 мВ, то можно, используя встроенное опорное напряжение и делитель из двух резисторов привести напряжение к нужному значению Попробуйте это сделать хотя бы за компьютером, вы лучше поймёте, как работать  со встроенными компараторами и источником опорного напряжения

Два микроконтроллера, использованные при экспериментах, выполняют каждый свою задачу В простейшем случае можно было осуществить всё, используя один микроконтроллер Но не всегда прерывание выполняемой микроконтроллером работы, чтобы выполнить другую задачу, возможно В подобных ситуациях второй микроконтроллер может взять на себя выполнение второй задачи Микроконтроллеры, как мы это сделали выше, можно соединить по UART, но в простых ситуациях можно использовать соединение (в нашем случае мы могли это сделать) выводов порта для обмена информацией Например, мы могли бы соединить выход второго микроконтроллера с входом  первого Состояние выхода второго микроконтроллера соответствовало бы состоянию флага (использованного в примере), а по состоянию выхода первый контроллер мог легко определить всё, что ему было бы нужно Вариантов, как сделать то или другое, обычно бывает достаточно много Остаётся только выбрать подходящий

Источник: Гололобов ВН,- Самоучитель игры на паяльнике (Об электронике для школьников и не только), – Москва 2012

Оставить комментарий

микросхемы мощности Устройство импульсов питания пример приемника провода витков генератора выходе напряжение напряжения нагрузки радоэлектроника работы сигнал сигнала сигналов управления сопротивление усилитель усилителя усиления устройства схема теория транзистора транзисторов частоты