btfss STATUS, Z ;проверяем результат на "0"
goto calc2 ;если результат не "0" идем на метку calc2
decf DIGIT3, 1 ;если результат равен "0" уменьшаем переменную DIGIT3 на "1"
goto calc5 ;выходим из подпрограммы т.к. достигнуто значение 99,9
;-----------------------------------------------------корректируем погрешность перевода
calc2 decfz LAPSE, 1 ;уменьшаем значение LAPSE на 1
goto calc3 ;если переменная LAPSE не равна "0" - идем на метку calc3
movlw d'57' ;записываем в аккумулятор значение "57"
movwf LAPSE ;записываем значение аккумулятора в переменную LAPSE
movlw d'2' ;записываем в аккумулятор значение "2"
addwf TIMER1, 1 ;прибавляем к переменной TIMER1 значение аккумулятора
goto calc3 ;идем на метку calc3
;-----------------------------------------------------корректируем переменные TIMER1 и TIMER2
calc1 addwf TIMER1, 1 ;прибавляем к переменной TIMER1 значение аккумулятора
movlw d'100' ;записываем в аккумулятор значение "100"
addwf TIMER1, 1 ;прибавляем к переменной TIMER1 значение аккумулятора
decf TIMER2 ;уменьшаем значение переменной TIMER2 на "1"
проверяем флаги регистра STATUS
btfss STATUS, C ;флаг C-переноса
btfsc STATUS, Z ;и флаг Z-нулевого результата
goto calc4 ;если результат не отрицательный-продолжаем
если Z=0 и C=0 значит результат отрицательный-
;---------------------------------------------------------------------------------------------------------calc5 return ;возврат из подпрограммы
;==============================================================
Блок-схема данной подпрограммы представлена на рис. 14. Поясним некоторые моменты. Принимая скорость звука равной 331,4 м/с, имеем 331,4*1000/1000000 мм/мкс или 0,3314 мм/мкс. Т.к. по условию задания точность измерений составляет 0,1 м, а измеренное нами время составляет двойную величину, то логично вести подсчет промежутками времени за которое ультразвук проходит 0,2 м. Т.е. 200/0,3314=603,5=(600+3,5) мкс. Каждые 600 мкс у нас накапливается погрешность в 3,5 мкс. 57*3,5=199,5≈200. Т.е. каждый промежуток времени 57*600 мкс у нас возникает погрешность в 200 мкс. Хотя она и составляет 1/3 от заданной точности мы, все равно будем ее учитывать. Принцип работы подпрограммы ясен из блок-схемы.
Рис. 14. Блок-схема подпрограммы calculation.
Заключение
В процессе выполнения курсового проекта, было спроектировано устройство ультразвукового измерения дальности. В пояснительной записке представлено подробное описание схемы устройства, описание программного обеспечения.
В приложении представлена принципиальная схема разработанного устройства и приведен листинг программы.
В ходе выполнения курсового проекта были решены следующие задачи:
· синтез и разработка принципиальной схемы устройства;
· разработка программного обеспечения;
· разработка конструкторской документации проекта (пояснительная записка).
1. В. С. Яценков «Микроконтроллеры Microchip. Практическое руководство».
2. Документация к контроллерам фирмы Microchip.
Приложения
;==============================================================
программа для ультразвукового дальномера
;==============================================================
список директив
list P=16C84 ;директива определяющая тип процессора
#include <P16C84.INC> ;файл, описывающий специфические переменные, соответствующие процессору
_config b'00000000000001' ;слово конфигурации CPU
;==============================================================
описание используемых переменных (назначение адресов ячеекдля хранения переменных)
NUMIMP equ 0x0C ;рабочая переменная для подсчета числа импульсов
TIMER1 equ 0x0D ;рабочая переменная для подсчета времени 1
TIMER2 equ 0x0E ;рабочая переменная для подсчета времени 2
LAPSE equ 0x0F ;рабочая переменная для подсчетапогрешности перевода времени
DIGIT1 equ 0x10 ;рабочая переменная индикатора дециметров
DIGIT2 equ 0x11 ;рабочая переменная индикатора метров
DIGIT3 equ 0x12 ;рабочая переменная индикатора декаметров
;==============================================================
исполняемая программа
org 0х000 ;вектор сброса процессора, начальный адрес
clrf PORTA ;очистили выходные защелки порта А
clrf PORTB ;и порта В
clrf TMR0 ;очистка таймера TMR0
bsf STATUS, RP0 ;включили банк 1
movlw b’00011110’ ;настроили на вывод линию RA0,
movwf PORTA ;остальные линии порта A на ввод
movlw b’00000000’ ;настроили на вывод все линии порта B
movwf PORTB ;RB0…RB7
bcf OPTION_REG, 7 ;включили подтягивающие резисторы
bcf OPTION_REG, 5 ;включили режим таймера для TMR0
bcf STATUS, RP0 ;включили банк 0
;==============================================================
main ;основная программа
call initialization ;вызываем подпрограмму инициализации
main1 call indication ;вызываем подпрограмму индикации
goto pressing ;вызываем подпрограмму обработки нажатия кнопки
main2 call transfer ;вызываем подпрограмму передачи импульсов
main3 goto waiting ;вызываем подпрограмму ожидания отраженного сигнала
main4 goto reception ;вызываем подпрограмму приема отраженного сигнала
main5 call calculation ;вызываем подпрограмму вычисления расстояния
;==============================================================
initialization ;подпрограмма инициализации и начальных условий
обнуляем значения используемых переменных
clrf PORTA ;очистили выходные защелки порта A
clrf NUMIMP ;обнуляем значение NUMIMP
clrf TIMER1 ;обнуляем значение TIMER1
clrf NUMCH ;обнуляем значение NUMCH
clrf TIMER2 ;обнуляем значение TIMER2
clrf LAPSE ;обнуляем значение LAPSE
clrf DIGIT1 ;обнуляем значение DIGIT1
clrf DIGIT2 ;обнуляем значение DIGIT2
clrf DIGIT3 ;обнуляем значение DIGIT3
устанавливаем значения используемых переменных
movlw d'5' ;помещаем значение "5" для NUMIMP в аккумулятор
movwf NUMIMP ;помещаем значение из аккумулятора в NUMIMP
movlw d'100' ;помещаем значение "100" для TIMER1 в аккумулятор
movwf TIMER1 ;помещаем значение из аккумулятора в TIMER1
movlw d'100' ;помещаем значение "100" для TIMER2 в аккумулятор
movwf TIMER2 ;помещаем значение из аккумулятора в TIMER2
movlw d'57' ;помещаем значение "57" для LAPSE в аккумулятор
movwf LAPSE ;помещаем значение из аккумулятора в LAPSE
return ;возврат из подпрограммы
;==============================================================
indication ;подпрограмма индикации измеренного расстояния
;-----------------------------------------------------устанавливаем биты подключения индикаторов
bsf IGIT1, 6 ;устанавливаем бит 6 переменной DIGIT1 в 1
bsf DIGIT2, 7 ;устанавливаем бит 7 (точка) переменной DIGIT2 в 1
bsf DIGIT2, 5 ;устанавливаем бит 5 переменной DIGIT2 в 1
bsf DIGIT3, 4 ;устанавливаем бит 4 переменной DIGIT3 в 1
;-----------------------------------------------------выводим значение DIGIT1 на индикатор
movf DIGIT1, 0 ;помещаем значение переменной DIGIT1 в аккумулятор
movwf PORTB ;выводим значение в порт В
устанавливаем задержку отображения
clrf TMR0 обнуляем таймер и
bcf INTCON, TOIF ;устанавливаем в 0 флаг прерывания по его переполнению
indc1 btfss INTCON, TOIF ;проверяем флаг прерывания по переполнению таймера
goto indc1 если флаг равен 0 (счетчик не переполнен)-выполняем проверку если флаг равен 1 (счетчик переполнен) - переходим к следующему индикатору
;-----------------------------------------------------выводим значение DIGIT2 на индикатор
movf DIGIT2, 0 ;помещаем значение переменной DIGIT1 в аккумулятор
movwf PORTB ;выводим значение в порт В
устанавливаем задержку отображения
clrf TMR0 ;обнуляем таймер и
bcf INTCON, TOIF ;устанавливаем в 0 флаг прерывания по его переполнению
indc2 btfss INTCON, TOIF ;проверяем флаг прерывания по переполнению таймера
goto indc2 если флаг равен 0 (счетчик не переполнен)-выполняем проверку если флаг равен 1 (счетчик переполнен) - переходим к следующему индикатору
;-----------------------------------------------------выводим значение DIGIT3 на индикатор
movf DIGIT3, 0 ;помещаем значение переменной DIGIT3 в аккумулятор
movwf PORTB ;выводим значение в порт В
;устанавливаем задержку отображения
clrf TMR0 ;обнуляем таймер и
bcf INTCON, TOIF ;устанавливаем в 0 флаг прерывания по его переполнению
indc3 btfss NTCON, TOIF ;проверяем флаг прерывания по переполнению таймера
goto indc3 ;если флаг равен 0 (счетчик не переполнен)-выполняем проверку если флаг равен 1 (счетчик переполнен)-
;---------------------------------------------------------------------------------------------------------
return ;возврат из подпрограммы
;==============================================================
pressing ;подпрограмма обработки нажатия кнопки
btfss PORTA, 2 ;проверяем линию RA2 порта А (кнопку s2),
goto main1 ;если не нажата возвращаемся в программу (на indication)
goto main2 ;если нажата-возврат из подпрограммы
;==============================================================
transfer ;подпрограмма передачи импульсов
;---------------------------------------------------------------------------------------------------------
movlw d'5' ;помещаем значение "5" для NUMIMP в аккумулятор
movwf NUMIMP ;помещаем значение из аккумулятора в NUMIMP
;-----------------------------------------------------передача сигнала
tran1 bsf PORTA, 0 ;устанавливаем в 1 линию RA0 порта А
movlw d'249' ;помещаем значение "249" для таймера в аккумулятор
movwf TMR0 ;помещаем значение из аккумулятора в таймер
bcf INTCON, TOIF ;устанавливаем в 0 флаг прерывания по переполнению таймера
tran2 btfss INTCON, TOIF ;проверяем флаг прерывания по переполнению таймера
goto tran2 ;если флаг равен 0 (счетчик не переполнен)-выполняем проверку
если флаг равен 1 (счетчик переполнен)-
;-----------------------------------------------------задержка сигнала
bcf PORTA, 0 ;устанавливаем в 0 линию RA0 порта А
movlw d'251' ;помещаем значение "251" для таймера в аккумулятор
movwf TMR0 ;помещаем значение из аккумулятора в таймер
bcf INTCON, TOIF ;устанавливаем в 0 флаг прерывания по переполнению таймера
tran3 btfss INTCON, TOIF ;проверяем флаг прерывания по переполнению таймера
goto tran3 ;если флаг равен 0 (счетчик не переполнен)-выполняем проверку
если флаг равен 1 (счетчик переполнен)-
;-----------------------------------------------------считаем импульсы
decfsz NUMIMP, 1 ;уменьшаем зачение NUMIMP на "1"если NUMIMP не равен "0" (передано<5импульсов)-
goto tran1 ;переходим в начало подпрограммы на tran1 если NUMIMP равен "0"
;-----------------------------------------------------(передано 5 импульсов)-
movlw d'3' ;помещаем значение "3" для NUMIMP в аккумулятор
movwf NUMIMP ;помещаем значение из аккумулятора в NUMIMP
;---------------------------------------------------------------------------------------------------------