LIST P=16f84 ;индикация для U питания = 3 в (ассемблер для 16F84 можно использовать для 16F819) include p16f819.inc __CONFIG 2F30H ;2F30H #define bank0 bcf STATUS,RP0 ;выбрать Bank 0 #define bank1 bsf STATUS,RP0 ;выбрать bank 1 ORG 0 goto st org 4 st clrf fl ;регистр флагов, биты 0=1 -была нажата кнопка 1=1 -кнопка была нажата > 4 сек,значит показываем значение без линейно-логарифмического преобразования 2=1 -кнопка отжата 3=1 -показываем значение без линейно-логарифмического преобразования ;при нажатии на кнопку устройство отключается, еще раз нажимаем - включается ;если нажать и удерживать > 4сек, то показывает значение без логарифмического преобразования movlw 0ff movwf n_kn ;счетчик времени нажатия кнопки movlw 1 movwf n_kn1 ;старший байт счетчика времени нажатия кнопки st0 call init st1 btfsc ADCON0,ADGO goto st1 ;ожидание готовности АЦП movlw 19 subwf ADRESH,w ;учитывам смещение напряжения на диодах детектора bc st2 ;если результат отрицательный, то не учитываем movf ADRESH,w ;вообще-то здесь будет ошибка измерения если напряжение смещения окажется меньше ожидаемого st2 movwf k ;результат измерения movwf kz btfss fl,0 goto st6 ;кнопка не нажималась btfss fl,1 goto wikl ;кнопка была нажата недостаточно долго - перейти в спящий режим bsf fl,3 ;кнопка была нажата > 4 сек,значит st6 btfss fl,3 ;показываем значение без линейно-логарифмического преобразования call preobr bsf ADCON0,ADGO ;запускаем АЦП (он работает сам, к следующему опросу (метка st1)результат будет готов call init_k ;пребразуем число в регистре kz в константы для подачи на индикатор movlw 10 ;количество циклов индикации (время показа результата измерения около 0,3сек) movwf t1 st3 btfss PORTB,6 ;опрос порта, goto st5 ;если нажата кнопка - переход call out ;вывод на индикатор-формирование временной диаграммы индикатора st4 decfsz t1,f goto st3 ;цикл индикации bsf fl,2 ;установить признак что кнопка не нажата goto st0 ;? st5 btfss fl,2 ;ожидание отпускания кнопки goto st3 ;для пpедотвpащения выключения после включения bank1 bsf PORTB,3 ;погасить часть сегментов на индикаторе bank0 btfsc fl,3 ;для выкл из pеж доп инд bcf fl,1 ; bsf fl,0 decfsz n_kn,f ;счетчик времени нажатия кнопки goto st3 decfsz n_kn1,f ;старший байт счетчика времени нажатия кнопки goto st3 bsf fl,1 ;кнопка была нажата > 4 сек,значит показываем значение без линейно-логарифмического преобразования goto st3 ;вывод на индикатор-формирование временной диаграммы индикатора out bank1 bsf PORTB,3 ;первый цикл диаграммы bank0 movf k3,w iorlw 2 ;погасить левую цифру ("1") movwf PORTA andlw 20 iorwf k1,w movwf PORTB bank1 bcf PORTB,6 ;включить верхние сегменты (-) bank0 call zdr bank1 bsf PORTB,6 ;второй цикл диаграммы bank0 movf k4,w iorlw 2 ;погасить левую цифру ("1") movwf PORTA andlw 20 iorwf k2,w movwf PORTB bank1 bcf PORTB,3 ;включить нижние сегменты (+) bank0 call zdr bank1 bsf PORTB,3 ;третий цикл диаграммы bank0 movf k3,w iorlw 2 ;погасить левую цифру ("1") xorlw 0ff movwf PORTA movf k3,w andlw 20 iorwf k1,w xorlw 0ff movwf PORTB bank1 bcf PORTB,6 ;включить верхние сегменты (-) bank0 call zdr bank1 bsf PORTB,6 ;четвертый цикл диаграммы bank0 movf k4,w iorlw 2 ;погасить левую цифру ("1") xorlw 0ff movwf PORTA movf k4,w andlw 20 iorwf k2,w xorlw 0ff movwf PORTB bank1 bcf PORTB,3 ;включить нижние сегменты (+) bank0 call zdr return init_k movf kz,w movwf k01 ;формирование адреса перехода для выбора константы movwf k02 swapf k01,f movlw 0f andwf k01,f andwf k02,f call tab1 movwf k1 call tab2 movwf k2 call tab3 movwf k3 call tab4 movwf k4 return init movlw 0 movwf INTCON ;без прерываний bank1 movlw 80 movwf OPTI ;отключить встроенные резисторы на ножках порта movlw 0 movwf OSCCON ;частота встроенного генератора 32кгц movlw 0 movwf OSCTUNE ;то же clrf ADCON1 ;все 5 ножек могут использоваться как входы АЦП movlw 048 movwf PORTB ;конфигурируем ножки на вход или выход movlw 38 movwf PORTA bank0 movlw 23 ;AN4 - вход АЦП, включить питание АЦП, запуск цикла измерения movwf ADCON0 return wikl movlw 10 ;выключить питание АЦП movwf ADCON0 movlw 0ff ; на выходы подать "1" movwf PORTA movwf PORTB bank1 movlw 0 movwf PORTA movlw 048 ;RB3 - на вход movwf PORTB call zdr bank0 movf PORTB,w ;для правильной работы прерывания movlw 88 ;разрешить прерывание от изменения на входе порта B movwf INTCON sleep ;спать goto st zdr clrf t ;просто временная задержка bsf t,4 zdr2 decfsz t,f goto zdr2 return tab1 movf k01,w ;переход на кол-во шагов соответствующих индицируемой цифре addwf PCL,f ;для выбора константы подаваемой на порт retlw 0c2 ;0 retlw 0d6 ;1 retlw 0c4 ;2 retlw 0c4 ;3 retlw 0d0 ;4 retlw 0c1 ;5 retlw 0c1 ;6 retlw 0c6 ;7 retlw 0c0 ;8 retlw 0c0 ;9 retlw 0d5 retlw 0d1 retlw 0d5 retlw 0d4 retlw 0c1 retlw 0d5 ;- retlw 0c1 ;f tab2 movf k01,w ;переход на кол-во шагов соответствующих индицируемой цифре addwf PCL,f ;для выбора константы подаваемой на порт retlw 18 ;0 retlw 1e ;1 retlw 19 ;2 retlw 1c ;3 retlw 1e ;4 retlw 1c ;5 retlw 18 ;6 retlw 1e ;7 retlw 18 ;8 retlw 1c ;9 retlw 18 retlw 18 retlw 19 retlw 18 retlw 19 retlw 1f ;- retlw 1b ;f tab3 movf k02,w ;переход на кол-во шагов соответствующих индицируемой цифре addwf PCL,f ;для выбора константы подаваемой на порт retlw 80 ;0 retlw 0a1 ;1 retlw 01 ;2 retlw 01 ;3 retlw 20 ;4 retlw 40 ;5 retlw 40 ;6 retlw 81 ;7 retlw 00 ;8 retlw 00 ;9 retlw 61 retlw 60 retlw 61 retlw 21 retlw 40 retlw 61 ;- retlw 40 ;f tab4 movf k02,w ;переход на кол-во шагов соответствующих индицируемой цифре addwf PCL,f ;для выбора константы подаваемой на порт retlw 20 ;0 retlw 0a1 ;1 retlw 60 ;2 retlw 21 ;3 retlw 0a1 ;4 retlw 21 ;5 retlw 20 ;6 retlw 0a1 ;7 retlw 20 ;8 retlw 21 ;9 retlw 20 retlw 20 retlw 60 retlw 20 retlw 60 retlw 0e1 ;- retlw 0e0 ;f preobr movlw 60 ;при нулевом входном сигнале показывать 60 db movwf kz clrf kx goto l2 l1 movlw 3 ;каждый сдвиг +3db addwf kz,f movf kz,w ;десятичная коррекция (чтобы были значения от 0 до 9) andlw 0f ; sublw 9 ; bc l2 ; movlw 6 ; addwf kz,f ; l2 bcf STATUS,C ;обнулить бит переноса rrf k,f ;сдвигаем вправо rrf kx,f movf k,w bnz l1 ;пока не обнулится k btfss kx,6 goto l3 incf kz,f ;+2db incf kz,f l3 btfsc kx,5 incf kz,f ;+1db movf kz,w ;десятичная коррекция (чтобы были значения от 0 до 9) andlw 0f sublw 9 bc l4 movlw 6 addwf kz,f l4 return cblock 20 :начальный адрес банка регистров (меньше 20 для 16F819 занимают спецрегистры) t ;счетчик для временной задержки t1 ;счетчик количества показов одного измерения k ;хранение результата АЦП - аналого-цифр.преобр. kx ;вспомогательный регистр для преобр.из линейной в логарифмическую зависимость kz ;результат линейно - логарифмической зависимости (шкала в децибелах db) k01 ;адрес перехода k02 ;адрес перехода k1 ;констаты для выдачи на порт (изображения символов) k2 ;констаты для выдачи на порт (изображения символов) k3 ;констаты для выдачи на порт (изображения символов) k4 ;констаты для выдачи на порт (изображения символов) n_kn ;младший байт счетчика времени нажатия кнопки n_kn1 ;старший байт счетчика времени нажатия кнопки fl ;регистр флагов для выбора режима работы endc end