Обучение программированию PIC контроллеров (Урок 4, часть 2)
|
|
sanyaav | Дата: Пятница, 08.02.2013, 21:46 | Сообщение # 1 |
Репутация:
Группа:Журналист
Сообщений: 134
Награды: 8
Статус:Offline
В первой программе на выходе у нас получились импульсы с частотой 166,666 кГц, их и "не слышо" - то есть пищать не будет, так как лежит за границей слышимого диапазона, и "не видно", так как мигание светодиода тоже не увидим. 1 вариантом будет мигание светодиода. Для начала определимся: 1 сек светодиод горит, 1-потушен. Для того, чтобы создать такою задержку нужно воспользоваться командой decfsz (декремент регистра F пока не установится ноль). Можно вставить её после команды bcf и bsf, но так как временной интервал задан один и тот же, то можно упростить программу используя ветку с командой decfsz только 1 раз, используя её как подпрограмму. Вызов подпрограмму осуществляется командой call, возврат из ПП осуществляется командой return. Алгоритм получится такой: вкл. GP0, ПП задержки, выкл. GP0, ПП задержки. введём команды вызова ПП задержки (назовём её PP_1_Sec):
START bcf GPIO,0 clrwdt nop call PP_1_Sec bsf GPIO,0 call PP_1_Sec goto START
Здесь уже можно убрать команду сброса сторожевого таймера, так как она будет испоотзоваться в ПП задержки, заменим её на команду nop, чтобы сохранить равными длительность высокого и низкого уровней.
Простейшая программа задержки выглядит так: .... .... movlw .255 ;пересылка в аккумулятор числа 255 (ВАЖНО!!! максимальное число которое может хранить регистр это FF-в шестнадцатеричной, или 255 в десятичной.) movwf IMP ; пересылка числа из аккумулятора в регистр IMP
met1 clrwdt ;сброс сторожевого таймера decfsz IMP,1 ;декремент регистра IMP, (цифра после показывает, где сохраняется результат, если 1, то в регистре IMP, если 0, то в аккумуляторе) goto met1 ; если результат не равен нулю, то программа выполнит эту команду goto Start ; если результат равен нулю, то выполнита эта команда, таким образом ПП задержки будет завершена
Теперь нужно посчитать, сколько машинных циклов выолнится в этой программе.
Считать начинаем после метки met1, команда clrwdt выполняется за 1 МЦ, то есть за 1 мкс., команда decfsz при не равенстве нулю выполняется за 1 МЦ, команда goto за 2 МЦ, итого получаем 4мкс. Всего будет 255 "колец" по 4 мкс. итого 1,02 мс, как можно догадаться 1 мс мало, нужно сделать ещё один цикл, у нас как бы получится цикл в цикле: 255*255*4мкс=0,26 с. тоже мало, добавляем 3 цикл: 255*255*255*4 мкс= 66 с. - хватает и даже с запасом. У нас как бы получится грубая и точная настройки. Сразу оговорюсь, расчёт временного промежутка неточен, произвожу его только для наглядности, в программе будет много "лишних" команд, которые будут добавлять каждый раз по 1 мкс. при выполнении. Если кто-то хочет точно отмерить 1 с. - добавляйте команду-пустышку nop в "кольцо" цикла.
В прошлой части урока я ввёл 1 регистр общего назначения IMP, для реализации цикла в цикле одного регистра будет мало, так как у нас получилось 3 "кольца" добавляем ещё 2 регистра IMP2 и IMP3 в шапку программы:
IMP equ 20h IMP2 equ 21h IMP3 equ 22h
Теперь делаем 3 кольца, я уже подобрал значения переменных, так чтобы длительность импульса приблизительно равнялась 1 с., оформляем как подпрограмму:
PP_1_Sec
movlw .39 movwf IMP
met movlw .50 movwf IMP2
met2 movlw .128 movwf IMP3
met3 clrwdt decfsz IMP3,1 goto met3
decfsz IMP2,1 goto met2
decfsz IMP,1 goto met
return
не забываем про end в конце.
Компилируем и проверяем в симуляторе MPLAB, как выбрать симулятор я уже рассказывал в уроке по MPLAB, теперь опишу как с ним работать. на панели появляются такие кнопки:
Основных кнопок три: первая кнопка служит для запуска программы и она будет выполнятся без остановки, вторая для паузы, и 4 для выполнения 1 команды. теперь нужно замерить временной интервал, делается это с помощью окна Stopwatch в меню Debugger, после запуска видим такое окно:
чтобы правильно "замерить" время нужно расставить точки остановки у команд bcf и bsf (можно конечно нажимать на 4 кнопку 1000000 раз, если кто то захочет, то займитесь на досуге ), для этого подводим курсор к нужной команде и нажимаем правой кнопкой, в появившемся меню выбираем пункт Set Breakpoint поставленные точки отображаются так:
Теперь нажимаем кнопку запуска и видим как программа остановилась у первой точки, а таймер показал нам 3 мкс
Нажимаем кнопку Zero в таймере и кнопку запуска программы как видим программа остановилась у второй точки и таймер показал нам время приближённо равное 1 секунде (повторюсь: всё это для наглядности, если кому-то нужно точное время используйте команду nop для калибровки).
теперь можно запустить выполнение программы в протеусе, в нашу схему нужно добавить светодиод, лезем в библиотеку и выбираем LED-RED, и резистор на 0,5 кОм (в симуляторе схема заработает и без резистора, а на практике светодиод без резистора сгорит, если нужно точно рассчитать резистор, то пользуйтесь законом Ома) собираем, запускаем, смотрим:
Теперь опишу второй вариант программы: Создание писка частотой 1000 Гц (опять же приближённо 1000, кому интересно подберите точные константы) Сам текст программы не изменится, изменения коснутся только констант. Чтобы определиться с временным интервалом нужно знать период, период для сигнался частотой 1000 гц равен 1/1000=1мс., и ещё разделить на 2, так как период-это высокий уровень+низкий уровень, 0,5мс - это 500 машинных циклов, то есть 1 "кольца" вполне хватит, но чтобы не менять программу подберём три значения, допустим первыми двумя константами будут 2, чтобы посчитать 2 константу нужно 500 МЦ разделить на 4мкс-время исполнения "малого кольца" и разделить на уже выбранные константы итого получаем: 500/4/2/2~31, запишем это число в IMP3 (забегая вперёд скажу, что там больше подойдёт число 29, избыток возникает из-за промежуточных команд mov) запускаем таймер в MPLAB и убеждаемся в правильности выполнения программы:
Теперь в проект в Протеусе добавим динамик, для того чтобы услышать звук, ищем элемент с названием sounder и подсоединяем его к GP0, запускаем, проверяем по осцилографу и не забудьте включить колонки, чтобы услышать звук (светодиод можно не отключать на практике он будет светиться наполовину):
файл asm и проект в протеусе качать ТУТ
Прошивка МК и реальные испытания в следующем уроке.....
Сообщение отредактировал sanyaav - Суббота, 09.02.2013, 16:22 | |
|
I'll be back
|
|
| |
Zloy | Дата: Суббота, 09.02.2013, 07:46 | Сообщение # 2 |
Репутация:
Группа:Проверенный паятель
Сообщений: 14
Награды: 0
Статус:Offline
Спасибо !!!!
| |
|
Я злой и страшный серый волк!!!!
|
|
| |
makarius | Дата: Воскресенье, 09.03.2014, 21:23 | Сообщение # 3 |
Репутация:
Группа:Проверенный паятель
Сообщений: 362
Награды: 12
Статус:Offline
Спасибо, наконец-то нашёл о программировании и отладке, полезно, если кто хочет осилить.
| |
|
Каждый выбирает для себя женщину, религию, дорогу. Дьяволу служить или пророку -...
|
|
| |
ivan142 | Дата: Суббота, 11.04.2015, 10:20 | Сообщение # 4 |
Репутация:
Группа:Проверенный паятель
Сообщений: 1
Награды: 0
Статус:Offline
а можно что нибудь по сложнее, например: на портах ввода вывода A,B,C,D,E , 7 сегментных светодиодными индикаторами и на 64 светодиода, при условии 1 семи сегментный индикатор должен работать в месте с светодиодами, а второй как счетчик, то есть допустим порт A для одного индикатора, порт C для другого индикатора, порт D для светодиодов, а порт Bдля всех индикаторов и светодиодов? сам принцип нужен как внести светодиоды в программу и как внести 7 сегментные индикаторы желательно с обьяснениями
Сообщение отредактировал ivan142 - Суббота, 11.04.2015, 10:25 | |
|
учение свет, а не ученье чуть свет и на работу
|
|
| |
sanyaav | Дата: Воскресенье, 12.04.2015, 01:51 | Сообщение # 5 |
Репутация:
Группа:Журналист
Сообщений: 134
Награды: 8
Статус:Offline
ivan142, алгоритм примерно такой: на схеме: к одному порту цепляем все индикаторы и диоды, семисегментные индикаторы параллельно, светодиоды делим по группам (8 штук в группе) и параллелим эти группы. Второй порт будет всё это коммутировать. на 2 порта можно повесить 64 светодиода (8 групп) или 2 индикатора и 48 диодов (6 групп). в программе: нужно зарезервировать 8 регистров для хранения информации поступающей на отображение. Написать ПП динамической индикации, которая будет по очереди забирать значения из этих регистров и выводить их в общий порт, потом нужно будет в порту, который коммутирует группы, установить в 1 тот пин, который соответствует регистру из которого считано значение, которое сейчас выведено в общий порт, установить паузу (моргание 100 Гц незаметно, поэтому пауза будет = 1/100 = 0,01 и ещё /8 = 0,00125 с.), программа для вычисления пауз есть на сайте Корабельникова. Повторить 8 раз. Вычисление значений для 7-сег. индикатора не составит труда, оно было описано в уроках. Вычисление значения для светодиодов ведётся аналогичным образом. только количество таблиц будет соответствовать количеству групп светодиодов (ну лично для меня это самый простейший путь). Я выложу схему тахометра на яву, там будут исходники.
| |
|
I'll be back
|
|
| |
Mirnay | Дата: Суббота, 08.07.2017, 06:38 | Сообщение # 6 |
Репутация:
Группа:Новичок
Сообщений: 4
Награды: 0
Статус:Offline
Поздно нашёл этот сайт. Объяснения очень понятные, спасибо автору. Может мне в мои 70 лет удастся постичь эту науку. У меня такой вопрос к автору как высчитываются константы, в частности .39, .50 , .128 откуда их брать. И как делать большие задержки по времени например реле времени. Если тема не заброшена конечно.
| |
|
|
|
| |
sanyaav | Дата: Суббота, 08.07.2017, 15:58 | Сообщение # 7 |
Репутация:
Группа:Журналист
Сообщений: 134
Награды: 8
Статус:Offline
Есть программа для расчета таких задержек
| |
|
I'll be back
|
|
| |
sanyaav | Дата: Суббота, 08.07.2017, 16:04 | Сообщение # 8 |
Репутация:
Группа:Журналист
Сообщений: 134
Награды: 8
Статус:Offline
Цитата Mirnay ( ) как высчитываются константы, в частности .39, .50 , .128 откуда их брать Это количество "колец"- проходов по командам программы, каждый проход - определенная задержка. Можно сделать основной цикл всего на 3 мкс, второй цикл - 5 проходов (константа .5), и в итоге получится 15 мкс., (ещё прибавится время выполнения команд из второго цикла), эти константы только для примера, на самом деле такая маленькая задержка программируется одним циклом.
| |
|
I'll be back
|
|
| |
Mirnay | Дата: Среда, 12.07.2017, 05:58 | Сообщение # 9 |
Репутация:
Группа:Новичок
Сообщений: 4
Награды: 0
Статус:Offline
За программку спасибо, очень мне поможет. И за разъяснения тоже. Буду разбираться дальше. Добавлено (11.07.2017, 21:46) --------------------------------------------- Как изменить выход на другие ножки МК. Используя команды mowlw и mowwf что-бы я попробовал переключится на другие. Добавлено (12.07.2017, 05:58) --------------------------------------------- Как задействовать другие ножки МК. Допустим они должны переключаться поочерёдно. Например GP0 и GP1.
| |
|
|
|
| |
sanyaav | Дата: Среда, 12.07.2017, 14:41 | Сообщение # 10 |
Репутация:
Группа:Журналист
Сообщений: 134
Награды: 8
Статус:Offline
нужно указать нужный выход в регистре TRIS (или сразу сделать все ножки как выходы), потом в программе устанавливать в 1 или 0 нужные биты регистра GPIO
| |
|
I'll be back
|
|
| |
Mirnay | Дата: Среда, 12.07.2017, 15:07 | Сообщение # 11 |
Репутация:
Группа:Новичок
Сообщений: 4
Награды: 0
Статус:Offline
Покажи пожалуйста как это сделать. Что-то не врублюсь не как. Виде примера кусок программы.
| |
|
|
|
| |