Фрагмент программы
Контроллер работает от RC генератора с частотой около 5 МГц.
На внешний вход таймера подается стабильная частота 32768 Гц, она является основой для тактовой частоты выборки сигнала.
; Рабочие переменные
F700_1 EQU 10 – массив значений корреляции для sin-ов и cos-ов частот
F700_2 EQU 11
F900_1 EQU 12
F900_2 EQU 13
F1100_1 EQU 14
F1100_2 EQU 15
F1300_1 EQU 16
F1300_2 EQU 17
F1500_1 EQU 18
F1500_2 EQU 19
F1700_1 EQU 1A
F1700_2 EQU 1B
N1 EQU 1C
N2 EQU 1D
BYTE1 EQU 1C – Первая половина эталонной константы
BYTE2 EQU 1D – Вторая половина эталонной константы
MAX_L EQU 1E
POINTER EQU 1E – Указатель на таблицу эталонных констант
CNT_SAMPL EQU 1F – Счетчик тактов
DETECT:
CLRWDT
MOVLW B'00100000' ; Внешний тактовый сигнал по перепаду 0/1
OPTION ; сигнал делится на 2
MOVLW 10H
MOVWF FSR
DET1:
CLRF INDF ; Очистить рабочие ячейки
INCF FSR
BTFSS FSR,5
GOTO DET1
CLRF FSR
MOVLW .152 ; Загрузка количества тактов в выборке
MOVWF CNT_SAMPL
; Цикл выборки. Сигнал считывается каждые 61.0325 мкс
WAIT_CIKL:
MOVF TMR0,W ; Приход внешнего сигнала определяется, когда
BTFSC STATUS,Z ; таймер принял значение отличное от нуля
GOTO WAIT_CIKL
CLRF TMR0
MOVF POINTER,W
CALL TABL ; Выборка эталонной константы
MOVWF BYTE1
INCF POINTER
MOVF POINTER,W
CALL TABL
MOVWF BYTE2
; SIG – вход сигнала
BTFSC SIG ; Если сигнал равен биту в эталоне то этот бит превратить в 0
COMF BYTE1
BTFSC SIG
COMF BYTE2
; Скоректировать размещение для нечетных по порядку констант
BTFSS CNT_SAMPL,0
GOTO DO_SUM
INCF POINTER
SWAPF BYTE1,W
ANDLW B'11110000'
MOVWF BYTE1
SWAPF BYTE2
MOVF BYTE2,W
ANDLW B'00001111'
IORWF BYTE1
DO_SUM:
; Подсчет величин корреляции
; Инкрементировать величину корреляции каждый раз, когда сигнал совпадает с эталоном
BTFSS BYTE1,7
INCF F700_1
BTFSS BYTE1,6
INCF F700_2
BTFSS BYTE1,5
INCF F900_1
BTFSS BYTE1,4
INCF F900_2
BTFSS BYTE1,3
INCF F1100_1
BTFSS BYTE1,2
INCF F1100_2
BTFSS BYTE1,1
INCF F1300_1
BTFSS BYTE1,0
INCF F1300_2
BTFSS BYTE2,7
INCF F1500_1
BTFSS BYTE2,6
INCF F1500_2
BTFSS BYTE2,5
INCF F1700_1
BTFSS BYTE2,4
INCF F1700_2
DECFSZ CNT_SAMPL
GOTO WAIT_CIKL ; 60 тактов контроллера на один такт выборки. МАКСИМУМ!
; Коррекция смещения результатов
MOVLW F700_1 ; Установит указатель на первую рабочую ячейку
MOVWF FSR
MOVLW .12
MOVWF CNT_SAMPL ;Количество циклов 12
MOVLW .76 ;Вычитать константу 152/2=76
; 5 тактов
DET4:
SUBWF INDF,F ; ( INDF - W )
BTFSS STATUS,C
COMF INDF
INCF FSR
DECFSZ CNT_SAMPL,F
GOTO DET4
; 7*12 = 84 такта
; Вычисление и поиск пары максимальных корреляций
CLRF SAMPL_CTN
CLRF MAX_L
MOVLW B'00100000' ; Указатель частоты
MOVWF CNT_SAMPL ; Загрузить указатель частоты
; 4 такта
; Поиск двух максимальных величин корреляции
DET5:
DECF FSR
MOVF INDF,W
DECF FSR
ADDWF INDF,F
MOVF SAMPL_CTN,W
SUBWF INDF,W ; ( [INDF] - SAMPL_CTN ) C=1 IF INDF>=SAMPL_CTN
BTFSS STATUS,C
GOTO DET6
MOVF SAMPL_CTN,W ; Сдвиг предыдущего верхнего максимума
MOVWF MAX_L ; в нижний максимум
MOVF N1,W ; Сдвиг соответствующего указателя частоты
MOVWF N2 ;
MOVF INDF,W
MOVWF SAMPL_CTN
MOVF CNT_SAMPL,W
MOVWF N1
GOTO DET7 ; Если величина попала в верхний максимум то она
DET6: ; уже не может быть записана в нижний
MOVF MAX_L,W
SUBWF INDF,W ; ( [INDF] - MAX_L ) C=1 IF INDF>=MAX_L
BTFSS STATUS,C
GOTO DET7
MOVF INDF,W
MOVWF MAX_L
MOVF CNT_SAMPL,W
MOVWF N2
DET7:
BCF STATUS,C
RRF CNT_SAMPL,F
BTFSS STATUS,C
GOTO DET5
; 22*6 = 132 такта
; Исходя из найденных частот с максимальными величинами корреляции
; по таблице вычисляем соответствующую цифру
MOVF N1,W
IORWF N2,F
CLRF SAMPL_COD
DET8:
MOVF SAMPL_COD,W
CALL TABL_CIPH
SUBWF N2,W ; N2 - W
BTFSC STATUS,Z
GOTO DET9
INCF SAMPL_COD
MOVF SAMPL_COD,W
XORLW .12
BTFSS STATUS,Z
GOTO DET8
MOVLW 0FFH
MOVWF SAMPL_COD
CLRF SAMPL_CTN
; 16*12 = 192 такта
DET9:
; Выход SAMPL_COD содержит цифру из диапазона 0..Bh, если 0FFh, то цифра не определена
; Максимальная продолжительность обработки цифры 417 тактов
RETLW 0