2.2 Код программы:
list p=12f675 ; list directive to define processor
#include <p12f675.inc> ; processor specific variable definitions
errorlevel -302 ; suppress message 302 from list file
__CONFIG _CP_OFF & _CPD_OFF & _BODEN_OFF & _MCLRE_ON & _WDT_OFF & _PWRTE_ON & _INTRC_OSC_NOCLKOUT
;***** Определение переменных
w_temp EQU 0x20 ; variable used for context saving
status_temp EQU 0x21 ; variable used for context saving
addata EQU 0x22 ; регистр выходного значения АЦП
davlenie EQU 0x24 ; регистр со значением давления
T_ EQU 0x25 ; регистр с временем задержки
N_ EQU 0x26 ; количество передаваемых бит
;**********************************************************************
ORG 0x000 ; processor reset vector
goto main ; go to beginning of program
ORG 0x004 ; interrupt vector location
izmerenie
BTFSC PIR1, ADIF ; прерывание от АЦП?
goto zapis ; да
BTFSS PIR1, TMR1IF ; прерывание от Т1?
retfie ; нет
BCF PIR1, TMR1IF ; отчистить флаг прер-я от Т1
BSF ADCON0, GO_DONE ; начать преобразование давления
; зажгём светодиод, который будет гореть во время работы АЦП
BSF GPIO, GP5
retfie
zapis
BCF GPIO, GP5 ; выключим индикатор работы АЦП
BCF PIR1, ADIF ; отчистить флаг прер-я от АЦП
MOVF ADRESH, w ; переносим данные из АЦП в буфер
MOVWF davlenie ; записываем данные в регистр
CLRF PIR1 ; отчистим флаги всех прерываний
peredacha ; передача значения давления с помощью SPI
MOVLW .8
MOVWF N_ ; счётчик передачи битов
BCF GPIO, GP4 ; сброс линии CS в 0
BSF STATUS, RP0 ; выбор 1-го банка
cikl
MOVLW .6
MOVWF T_ ; счётчик задержки = 6
RLF davlenie, 1 ; сдвиг влево регистра со значением давления
BTFSS STATUS, C
BCF TRISIO, 1 ; передача нуля
NOP ; оставляем высокий уровень на линии, передача "1"
; либо для получения стабильного "0"
BSF TRISIO, 2 ; начало такта
vremja
DECFSZ T_, f ; задержка такта на 17 мкс
; 5+5*2+2 = 17 мкс
goto vremja
BCF TRISIO, 2 ; конец такта
BSF TRISIO, 1 ; установка единицы на линии данных
DECFSZ N_, f
goto cikl
BCF STATUS, RP0 ; банк 0
retfie ; выход из прерывания
; these first 4 instructions are not required if the internal oscillator is not used
main
call 0x3FF ; retrieve factory calibration value
bsf STATUS,RP0 ; set file register bank to 1
movwf OSCCAL ; update register with factory cal value
BCF STATUS, RP0 ; выбираем 0-й банк
; настройка МК
CLRF GPIO ; отчистка портов
CLRF INTCON ; выключаем все прерывания
;*** настройка ТАЙМЕРА 1 ***
; Переполение таймера через 0,52 с.
; 255*255*8=0,5202 с
CLRF T1CON ; выключаем т1, сбрасываем предделитель
; внутренний такт. сигнал
CLRF TMR1H ; Очистка старшего
CLRF TMR1L ; и младшего разряда т1
BSF STATUS, RP0 ; выбираем 1-й банк
CLRF PIE1 ; выключаем прерывания от периферии
BCF STATUS, RP0 ; выбираем 0-ой банк
CLRF PIR1 ; очистка флагов от прерывания периферии
MOVLW b'00110101' ; Предделитель 1:8, т1 вкл,
MOVWF T1CON ; таймер 1 включен.
;*** конец настройки Т1 ***
BSF STATUS, RP0 ; выбираем 1-й банк
MOVLW b'00011000' ; предделитель перед WDT, приращение TMR0 по фронту
MOVWF OPTION_REG
; настройка АЦП
MOVLW b'00011111'
MOVWF TRISIO ; все порты настроены на вход, кроме GP5
BSF ANSEL, 5
BSF ANSEL, 4 ; 2-6 мкс на получения одного бита от АЦП
BSF ANSEL, 0 ; Аналоговый вход на GP0
BCF STATUS, RP0 ; выбираем 0-й банк
CLRF ADCON0
BSF ADCON0, ADON ; включен АЦП
; конец настройки АЦП
MOVLW b'11000000' ; разрешение глобальных прерываний и
MOVWF INTCON ; прерываний от периферии
BSF INTCON, PEIE ; прерывания от периферии вкл.
BSF INTCON, GIE ; глоб. прер. вкл.
BSF STATUS, RP0 ; выбираем 1-й банк
BCF TRISIO, 2 ; низкий уровень сигнала SCLK
BSF PIE1, ADIE ; прерывание от АЦП вкл.
BSF PIE1, T1IE ; прерывание от Т1 вкл.
BCF STATUS, RP0 ; банк 0
loop
goto loop ; ожидание прерывания от т1 или АЦП
; initialize eeprom locations
ORG 0x2100
DE 0x00, 0x01, 0x02, 0x03
END ; directive 'end of program'