;*************************************************************************
;
; Original header file for PIC 16F84 & AKIZUKI’s assembler.
; Copyright (c) 1998 by 32 Technical Laboratory (JG6DFK/QRP).
; All rights reserved.
;
;*************************************************************************
.16f84
;-------------------------------------------------------------------------
; Register definitions of bank 0.
;-------------------------------------------------------------------------
indf equ 00h ; Data I/O port for indirect addressing.
tmr0 equ 01h ; 8bits real-time cLOCk/counter.
pcl equ 02h ; Low order 8bits of the program counter. (PC)
status equ 03h ; Status register.
fsr equ 04h ; Indirect data memory address pointer 0.
porta equ 05h ; I/O ports A. (= RA0 to RA4)
portb equ 06h ; I/O ports B. (= RB0 to RB7)
ra equ 05h ; Same as PORTA.
rb equ 06h ; Same as PORTB.
eEDAta equ 08h ; EEPROM data register.
eeadr equ 09h ; EEPROM address register.
pclath equ 0Ah ; Write buffer for upper 5 bits of the PC.
iNTCon equ 0Bh ; Interrupt control register.
;-------------------------------------------------------------------------
; Register definitions of bank 1.
;-------------------------------------------------------------------------
option equ 01h ; (= 81h) Option register.
trISA equ 05h ; (= 85h) I/O ports A data direction register.
trisb equ 06h ; (= 86h) I/O ports B data direction register.
eecon1 equ 08h ; (= 88h) EEPROM data memory R/W status register.
eecon2 equ 09h ; (= 89h) I/O port for EEPROM data memory.
;-------------------------------------------------------------------------
; Others.
;-------------------------------------------------------------------------
; ----- For status register.
irp equ 7 ; Register bank select bit for indirect addressing.
rp1 equ 6 ; RP1:RP0 00 = Bank 0, 01 = Bank 1.
rp0 equ 5 ; 10 = Bank 2, 03 = Bank 3.
to equ 4 ; Time-out bit.
pd equ 3 ; Power-down bit.
z equ 2 ; Zero bit.
dc equ 1 ; Digit carry or bollow bit.
c equ 0 ; Carry or borrow bit.
; ----- For interrupt control register.
gie equ 7 ; Global interrupt enable bit.
eeie equ 6 ; EEPROM write complete interrupt enable bit.
t0ie equ 5 ; TMR0 overflow interrupt enable bit.
inte equ 4 ; RB0/INT interrupt enable bit.
rbie equ 3 ; RB port change interrupt enable bit.
t0if equ 2 ; TMR0 overflow interrupt flag bit.
intf equ 1 ; RB0/INT interrupt flag bit.
rbif equ 0 ; RB port change interrupt flag bit.
; ----- For option register.
rbpu equ 7 ; I/O ports B pull-up disable bit.
intedg equ 6 ; Interrupt edge select bit.
t0cs equ 5 ; TMR0 clock source select bit.
t0se equ 4 ; TMR0 source edge select bit.
psa equ 3 ; Prescaler Assignment bit.
ps2 equ 2 ; PS2:PS0 = Prescaler rate select bits.
ps1 equ 1 ; For TMR0 = 1:2 to 1:256.
ps0 equ 0 ; WDT = 1:1 to 1:128.
; ----- For I/O ports A. (RA)
ra4 equ 4 ; RA4/T0CKI.
t0cki equ 4 ; Same as ’ra4’.
ra3 equ 3 ; RA3.
ra2 equ 2 ; RA2.
ra1 equ 1 ; RA1.
ra0 equ 0 ; RA0.
; ----- For I/O ports B. (RB)
rb7 equ 7 ; RB7.
rb6 equ 6 ; RB6.
rb5 equ 5 ; RB5.
rb4 equ 4 ; RB4.
rb3 equ 3 ; RB3.
rb2 equ 2 ; RB2.
rb1 equ 1 ; RB1.
rb0 equ 0 ; RB0.
int equ 0 ; Same as ’rb0’.
; ----- For EEPROM control register. (EECON1)
eeif equ 4 ; EEPROM write operation interrupt flag bit.
wrerr equ 3 ; EEPROM write error flag bit.
wren equ 2 ; EEPROM write enable bit.
wr equ 1 ; EEPROM write control bit.
rd equ 0 ; EEPROM read control bit.
; ----- For general
w equ 0 ; Destination selector. (Working register)
f equ 1 ; Destination selector. (Register file)
;*************************************************************************
;
; SOFtware for Frequency Counter model PIC-FC1.
; Version 1.00.
;
; Copyright (c) 1999 by 32 Technical Laboratory. (JG6DFK/QRP)
; All rights reserved.
;
;*************************************************************************
; I/O assignment:
; RA4 (PIN 3) Input. (I)
; RA3 (pin 2) LCD Data #3. (O)
; RA2 (pin 1) LCD Data #2. (O)
; RA1 (pin 18) LCD Data #1. (O)
; RA0 (pin 17) LCD Data #0. (O)
; RB7 (pin 13) LCD Load Enable. (O)
; RB6 (pin 12) LCD Register Select. (O)
; RB5 (pin 11) Display Mode. (I)
; RB4 (pin 10) External prescaler mode. (I)
; RB3 (pin 9) Internal prescaler mode #1. (I)
; RB2 (pin 8) Internal prescaler mode.#0. (I)
; RB1 (pin 7) Gate time #1. (I)
; RB0 (pin 6) Gate time #0. (I)
.include 16f84_32.h
.osc xt ; Clock = 10 MHz.
.wdt off
.pwrt on
.protect off
id 0100h ; = Version No.
;-------------------------------------------------------------------------
; Equations.
;-------------------------------------------------------------------------
; ----- I/O difinitions.
LCD_LE equ rb7 ; LCD load enable.
LCD_RS equ rb6 ; LCD register select.
I_SELDSP equ rb5 ; Display mode select SW.
I_EXTPSC equ rb4 ; External prescaler select SW.
I_INTPS1 equ rb3 ; External prescaler select SW #1.
I_INTPS0 equ rb2 ; External prescaler select SW #0.
I_SELRS1 equ rb1 ; Resolution select SW #1.
I_SELRS0 equ rb0 ; Resolution select SW #0.
; ----- Constants.
FRES_1 equ 0 ; Resolution mode = 1 Hz.
FRES_10 equ 1 ; 10 Hz.
FRES_100 equ 2 ; 100 Hz.
FRES_1000 equ 3 ; 1 kHz.
DSP_FREQ equ 0 ; Display mode = frequency.
DSP_LENG equ 1 ; wave length. (X.XXX m)
IPSC_1 equ 0 ; Internal prescaler = 1:1.
IPSC_4 equ 1 ; 1:4.
IPSC_8 equ 2 ; 1:8.
IPSC_16 equ 3 ; 1:16.
TMR0_1 equ 00101000b ; Prescaler rate for TMR0 = 1:1.
TMR0_4 equ 00100001b ; 1:4.
TMR0_8 equ 00100010b ; 1:8.
TMR0_16 equ 00100011b ; 1:16.
XPSC_OFF equ 0 ; External prescaler = disabLED.
XPSC_ON equ 1 ; enabled.
XPSC_RATE equ 64 ; External prescaler rate.
MAXDIGIT equ 10 ; Max digit = "XXXXXXX.XXX".
; ----- LCD functions.
L_SELDR equ 0 ; LCD data register select.
L_FNCSET equ 00101000b ; LCD function set.
L_ENTSET equ 00000110b ; LCD entry mode set.
L_DSPCLR equ 00000001b ; LCD display clear.
L_DSPOFF equ 00001000b ; LCD display OFF.
L_DSPON equ 00001100b ; LCD display ON.
L_CSHOME equ 00000010b ; LCD cursor position reset.
L_DDFREQ equ 10000000b+01h ; LCD "Frequency" DD RAM addr.
L_DDMODE equ 10000000b+4Ch ; LCD "Mode" DD RAM addr.
L_DDINP1 equ 10000000b+40h ; LCD "Input" DD RAM addr1.
L_DDINP2 equ 10000000b+46h ; LCD "Input" DD RAM addr2.
L_DDGATE equ 10000000b+4Fh ; LCD "Gate" DD RAM addr.
;-------------------------------------------------------------------------
; Register file (= Work area) definitions.
;
; Notes: Lower byte is located first on long length variables.
; $ $+1 $+2
; (Intel format. Ex: 186A0h -> A0 86 01)
;-------------------------------------------------------------------------
org 0Ch
; ----- General.
I ds 4 ; General loop counter.
X ds 4 ; Source register for long word calc.
EX ds 4 ; Extra source register for mul/div.
Y ds 4 ; Destination register for long word calc.
EY ds 4 ; Extra dest. register for mul/div.
; ----- For count procedure.
CNTMODE ds 1 ; Temporary input buffer.
DSPMODE ds 1 ; Display mode.
EXT_PSC ds 1 ; External prescaler mode.
INT_PSC ds 1 ; Internal prescaler mode.
RESMODE ds 1 ; Resolution mode.
GATETIME ds 2 ; Gate time in milliseconds.
RTC_OLD ds 1 ; RTCC previous value.
RTC_NEW ds 1 ; RTCC new value.
CNT ds 3 ; Count value.
; ----- For LCD procedure.
LCD_RSEL ds 1 ; LCD register select.
LCD_DATA ds 1 ; LCD command or character data.
LCD_STRBUF ds MAXDIGIT ; LCD string buffer.
LCD_DPOINT ds 1 ; LCD decimal point location.
LCD_FXMPTR ds 1 ; LCD fixed message pointer.
; ----- For calculation procedure.
MDLOOPCT ds 1 ; Loop counter for mul/div.
CALCTMP1 ds 5 ; Temporary buffer for calculation.
CALCTMP2 ds 5 ; Temporary buffer for calculation.
; ----- For wait procedure.
WAIT1 ds 1 ; For large loop.
WAIT2 ds 1 ; For small loop.
;-------------------------------------------------------------------------
; Program entry.
;-------------------------------------------------------------------------
org 0
goto main
nop
nop
nop
goto main
;-------------------------------------------------------------------------
; String tables.
;-------------------------------------------------------------------------
s_kHz
retlw ’ ’ ; "kHz".
retlw ’k’ ;
retlw ’H’ ;
retlw ’z’ ;
retlw 0 ;
s_MHz
retlw ’ ’ ; "MHz".
retlw ’M’ ;
retlw ’H’ ;
retlw ’z’ ;
retlw 0 ;
s_m
retlw ’ ’ ; "m ".
retlw ’m’ ;
retlw ’ ’ ;
retlw ’ ’ ;
retlw 0 ;
s_LFMode
retlw ’L’ ; "LF".
retlw ’F’ ;
retlw 0 ;
s_MFmode
retlw ’M’ ; "MF".
retlw ’F’ ;
retlw 0 ;
s_MHmode
retlw ’M’ ; "MH".
retlw ’H’ ;
retlw 0 ;
s_HFmode
retlw ’H’ ; "HF".
retlw ’F’ ;
retlw 0 ;
s_xpsHDR
retlw ’I’ ; "INPUT".
retlw ’N’ ;
retlw ’P’ ;
retlw ’U’ ;
retlw ’T’ ;
retlw ’:’ ;
retlw 0 ;
s_xpsOFF
retlw ’A’ ; "A".
retlw 0 ; (External prescaler:OFF)
s_xpsON
retlw ’B’ ; "B".
retlw 0 ;(External prescaler:ON)
s_over
retlw ’T’ ; "Too Long !!"
retlw ’o’ ;
retlw ’o’ ;
retlw ’ ’ ;
retlw ’L’ ;
retlw ’o’ ;
retlw ’n’ ;
retlw ’g’ ;
retlw ’ ’ ;
retlw ’!’ ;
retlw ’!’ ;
retlw 0 ;
;-------------------------------------------------------------------------
; Data tables.
;-------------------------------------------------------------------------
; ----- Get Internal prescaler rate. -------------------------------------
get_iprate
addwf pcl, f
retlw 1 ; 1:1.
retlw 4 ; 1:4.
retlw 8 ; 1:8.
retlw 16 ; 1:16.
; ----- Get Internal prescaler rate for TMR0. ----------------------------
get_iprtm0
addwf pcl, f
retlw TMR0_1 ; 1:1.
retlw TMR0_4 ; 1:4.
retlw TMR0_8 ; 1:8.
retlw TMR0_16 ; 1:16.
; ----- Get message address of internal prescaler mode. ------------------
get_ipmptr
addwf pcl, f
retlw s_LFmode ; "LF".
retlw s_MFmode ; "MF".
retlw s_MHmode ; "MH".
retlw s_HFmode ; "HF".
; ----- Get decimal point location. --------------------------------------
get_dploc
addwf pcl, f
retlw 3 ; X.XXX kHz.
retlw 5 ; X.XXXXX MHz.
retlw 4 ; X.XXXX MHz.
retlw 3 ; X.XXX MHz.
;-------------------------------------------------------------------------
; Interrupt procedure.
;-------------------------------------------------------------------------
; No interrupt procedure.
;-------------------------------------------------------------------------
; Main procedure.
;-------------------------------------------------------------------------
main
; *** Initialize registers ***
clrf pclath ; Select program memory bank #0.
MOV lw 00000000b ; Disabled all interrupt
MOV wf intcon ; sources.
clrf porta ; Initialize I/O ports.
clrf portb ;
bsf status, rp0 ; Select bank 1.
MOV lw 00101000b ; Pull-up PORTB, T0CS = EXT &
MOV wf option ; set TMR0 rate. (1:1)
MOV lw 00010000b ; Set data directions.
MOV wf trisa ; 1: as input.
MOV lw 00111111b ;
MOV wf trisb ;
bcf status, rp0 ; Select bank 0. (Default)
MOV lw 11110000b ; Set all output ports to ’0’.
andwf porta, f ;
MOV lw 00111111b ;
andwf portb, f ;
; *** Initialize variable ***
clrf CNT+0 ; Clear counter for
clrf CNT+1 ; dummy display.
clrf CNT+2 ;
; *** Initialize LCD ***
call init_LCD ; Contains function set & clear screen.
call dsp_fixmsg ; Display fixed message.
; *** Main Loop ***
mainloop
call set_cntmode ; Set count mode. (Gate time etc.)
call dsp_status ; Display status.
MOV f DSPMODE, f ; Check display mode.
btfss status, z ;
goto len_mode ;
call dsp_freq ; Display frequency.
goto cntstart
len_mode
call dsp_leng ; Display wave length.
cntstart
call dsp_goff ; Display "Gate OFF".
call dsp_gon ; Display "Gate ON".
call count ; Count core.
goto mainloop
;-------------------------------------------------------------------------
; Set count mode.
; Input : Port B (Data input port of count mode)
; Output: DSPMODE (Display mode)
; EXT_PSC (External prescaler mode)
; INT_PSC (Internal prescaler mode)
; RESMODE (Resolution mode)
; GATETIME (Gate time in milliseconds)
; W register & variable I will be broken.
;
; Notes: All input ports are negative logic.
;-------------------------------------------------------------------------
set_cntmode
; *** Get count mode from input port ***
MOV f portb, w ; Read input port &
andlw 00111111b ; negate logic.
xorlw 00111111b ;
MOV wf CNTMODE ;
andlw 00000011b ; Get resolution mode.
MOV wf RESMODE ;
rrf CNTMODE, f ; Get internal prescaler mode.
rrf CNTMODE, f ;
MOV f CNTMODE, w ;
andlw 00000011b ;
MOV wf INT_PSC ;
rrf CNTMODE, f ; Get external prescaler mode.
rrf CNTMODE, f ;
MOV f CNTMODE, w ;
andlw 00000001b ;
MOV wf EXT_PSC ;
rrf CNTMODE, f ; Get display mode.
MOV f CNTMODE, w ;
andlw 00000001b ;
MOV wf DSPMODE ;
; *** Set gate time ***
MOV lw FRES_100 ; Set gate time soon if
subwf RESMODE, w ; resolution >= 100 Hz.
btfsc status, c ;
goto set_gtime ;
MOV f EXT_PSC, f ; Check other mode
btfsc status, z ; if external prescaler is enabled &
goto set_gtime ; internal prescaler rate <> 1:1.
;
MOV f INT_PSC, f ;
btfsc status, z ;
goto set_gtime ;
MOV lw IPSC_16 ; Resolution = 100 Hz if
subwf INT_PSC, w ; internal prescaler rate = 1:16,
MOV lw FRES_10 ; else resolution = 10 Hz.
btfsc status, c ;
MOV lw FRES_100 ;
;
MOV wf RESMODE ;
set_gtime
MOV lw 1 ; X <- external prescaler rate
MOV f EXT_PSC, f ; * internal prescaler rate
btfss status, z ; * 1000.
MOV lw XPSC_RATE ;
;
MOV wf X+0 ;
clrf X+1 ;
clrf X+2 ;
clrf X+3 ;
;
MOV f INT_PSC, w ;
call get_iprate ;
MOV wf Y+0 ;
clrf Y+1 ;
clrf Y+2 ;
clrf Y+3 ;
;
call mul_xy ;
;
MOV lw 0e8h ;
MOV wf Y+0 ;
MOV lw 03h ;
MOV wf Y+1 ;
call mul_xy ;
MOV lw 10 ; X <- X / 10 while I > 0.
MOV wf Y+0 ;(Skip soon if RESMODE = FRES_1)
clrf Y+1 ;
;
MOV f RESMODE, w ;
btfsc status, z ;
goto end_sgt ;
;
MOV wf I ;
sgt_loop ;
call div_xy ;
;
decfsz I ;
goto sgt_loop ;
end_sgt
MOV f X+0, w ; GATETIME <- X.
MOV wf GATETIME+0 ;
MOV f X+1, w ;
MOV wf GATETIME+1 ;
; *** Set Internal prescaler rate ***
MOV f INT_PSC, w ; Get TMR0 rate.
call get_iprtm0 ;
bsf status, rp0 ; Select bank 1.
MOV wf option ; set new TMR0 rate.
bcf status, rp0 ; Select bank 0. (Default)
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; Count procedure.
; Input : GATETIME (Gate time in milliseconds)
; Output: CNT (Value)
; W register & variable I, X, Y will be broken.
;-------------------------------------------------------------------------
count
; *** Prologue ***
MOV f GATETIME+0, w ; I <- GATETIME * 100.
MOV wf X+0 ; (Convert milliseconds to
MOV f GATETIME+1, w ; 10 microseconds)
MOV wf X+1 ;
clrf X+2 ; I: Count loop counter.
clrf X+3 ; (Use lower 24 bits)
;
MOV lw 64h ;
MOV wf Y+0 ;
clrf Y+1 ;
clrf Y+2 ;
clrf Y+3 ;
;
call mul_xy ;
;
MOV f X+0, w ;
MOV wf I+0 ;
MOV f X+1, w ;
MOV wf I+1 ;
MOV f X+2, w ;
MOV wf I+2 ;
clrf CNT+0 ; Clear pulse counter.
clrf CNT+1 ;
clrf CNT+2 ;
; Clear RTCC & init OLD value of RTCC.
clrw ;(But you may not clear it)
MOV wf tmr0 ; RTCC is disabled to increment
MOV wf RTC_OLD ; for 2 instruction cycles after
nop ; it is modified.
MOV lw 7 ; Wait 10 microseconds.
MOV wf I+3 ;
;
decfsz I+3 ;
goto $-1 ;
nop ;
nop ;
nop ;
; *** Pulse counter (Gate time = 10 microseconds * I) ***
pulse_cnt
MOV f tmr0, w ; Increment pulse counter.
MOV wf RTC_NEW ;
MOV f RTC_OLD, w ;
subwf RTC_NEW, w ;
;
addwf CNT+0, f ;
MOV lw 1 ;
btfsc status, c ;
addwf CNT+1, f ;
btfsc status, c ;
addwf CNT+2, f ;
MOV f RTC_NEW, w ; OLD <- NEW.
MOV wf RTC_OLD ;
MOV lw 1 ; Decrement counter for sub loop.
subwf I+0, f ;
btfss status, c ;
subwf I+1, f ;
btfss status, c ;
subwf I+2, f ;
nop ; Trim.
MOV f I+0, w ; Continue if I > 0.
iorwf I+1, w ;
iorwf I+2, w ;
btfss status, z ;
goto pulse_cnt ;
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; Init LCD.
; Input : None.
; Output: Port A, Port B (Data output port for LCD)
; LCD_RSEL (LCD register select which always 0)
; W register & variable LCD_DATA, I will be broken.
;
; Notes: Waiting time is about execution time * 2.7.
;-------------------------------------------------------------------------
init_LCD
; *** Power ON wait ***
MOV lw 100 ; Power ON wait for LCD.
call wait_ms ; (>= 15 milliseconds)
; *** Function set (Dummy #1) ***
clrf LCD_RSEL ; RS = ’0’.
bcf portb, LCD_RS ; (Default)
MOV lw 11110000b ; Function set.
andwf porta, f ; (Data bus = 8 bits)
MOV lw 00000011b ;
iorwf porta, f ;
MOV lw 3 ; Repeat 3 times.
MOV wf I ;
Li_fsloop
bsf portb, LCD_LE ; Strobe.
nop ;
nop ;
bcf portb, LCD_LE ;
MOV lw 5 ; Wait >= 4.1 milliseconds.
call wait_ms ;
decfsz I ; Continue if I > 0.
goto Li_fsloop ;
; *** Function set (Dummy #2) ***
MOV lw 11110000b ; Function set.
andwf porta, f ; (Data bus = 4 bits)
MOV lw 00000010b ;
iorwf porta, f ;
bsf portb, LCD_LE ; Strobe.
nop ;
nop ;
bcf portb, LCD_LE ;
call wait_100us ; Wait >= 100 microseconds.
; *** Function set (Real) ***
MOV lw L_FNCSET ; Set real function.
call set_LCD ;
; *** Others ***
MOV lw L_DSPOFF ; Display OFF.
call set_LCD ;
call cls ; Clear display.
MOV lw L_ENTSET ; Set entry mode.
call set_LCD ;
MOV lw L_DSPON ; Display ON.
call set_LCD ;
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; Display fixed message.
; Input : None.
; Output: None.
; W register, variable LCD_DATA & LCD_FXMPTR will be broken.
;-------------------------------------------------------------------------
dsp_fixmsg
; *** Display message ***
MOV lw L_DDINP1 ; Set cursor to "Input".
call set_LCD ; (Header message)
MOV lw s_xpshdr ; Display header message of
MOV wf LCD_FXMPTR ; input channel.
call dsp_fixstr ; (External prescaler)
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; Display status.
; Input : INT_PSC (Internal prescaler mode)
; EXT_PSC (External prescaler mode)
; Output: None.
; W register, variable LCD_FXMPTR will be broken.
;-------------------------------------------------------------------------
dsp_status
; *** Display internal prescaler mode ***
MOV lw L_DDMODE ; Set cursor to "Mode".
call set_LCD ;
MOV f INT_PSC, w ; Get message address.
call get_ipmptr ;
MOV wf LCD_FXMPTR ; Display internal prescaler mode.
call dsp_fixstr ;
; *** Display Input channel (Ext. prescaler mode) ***
MOV lw L_DDINP2 ; Set cursor to "Input".
call set_LCD ; (Core)
MOV lw s_xpsOFF ; Set message address.
MOV f EXT_PSC, f ;
btfss status, z ;
MOV lw s_xpsON ;
MOV wf LCD_FXMPTR ; Display input channel.
call dsp_fixstr ;
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; Display "Gate Open".
; Input : None.
; Output: None.
; W register will be broken.
;-------------------------------------------------------------------------
dsp_gon
; *** Display message ***
MOV lw L_DDGATE ; Set cursor to "Gate".
call set_LCD ;
bsf LCD_RSEL, L_SELDR ; Select data register.
MOV lw ’*’ ; Set gate sign.
call set_LCD ;
clrf LCD_RSEL ; Set to default.
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; Display "Gate Close".
; Input : None.
; Output: None.
; W register & variable LCD_DATA will be broken.
;-------------------------------------------------------------------------
dsp_goff
; *** Display message ***
MOV lw L_DDGATE ; Set cursor to "Gate".
call set_LCD ;
bsf LCD_RSEL, L_SELDR ; Select data register.
MOV lw ’ ’ ; Clear gate sign &
MOV wf LCD_DATA ; wait.
call set_LCDcmd ;
MOV lw 100 ;
call wait_ms ;
clrf LCD_RSEL ; Set to default.
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; Display frequency.
; Input : CNT (Count value)
; RESMODE (Resolution mode)
; Output: None.
; W register, variable X, EX, Y, EY, LCD_DPOINT & LCD_FXMPTR
; will be broken.
;-------------------------------------------------------------------------
dsp_freq
; *** Set cursor location of LCD & convert count data to string ***
MOV lw L_DDFREQ ; Set cursor to "frequency".
call set_LCD ;
MOV f CNT+0, w ; Change count data to
MOV wf X+0 ; string.
MOV f CNT+1, w ;
MOV wf X+1 ;
MOV f CNT+2, w ;
MOV wf X+2 ;
clrf X+3 ;
clrf EX+0 ;
clrf EX+1 ;
clrf EX+2 ;
clrf EX+3 ;
call x_to_str ;
; *** Display frequency ***
MOV f RESMODE, w ; Set decimal point location.
call get_dploc ;
MOV wf LCD_DPOINT ;
call dsp_value ; Display value.
MOV lw s_kHz ; Add unit. (kHz or MHz)
MOV f RESMODE, f ;
btfss status, z ;
MOV lw s_MHz ;
;
MOV wf LCD_FXMPTR ;
call dsp_fixstr ;
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; Display wave length.
; Input : CNT (Count value)
; RESMODE (Resolution mode)
; Output: None.
; W register, variable I, X, EX, Y, EY, LCD_DPOINT & LCD_FXMPTR
; will be broken.
;-------------------------------------------------------------------------
dsp_leng
; *** Set cursor location of LCD ***
MOV lw L_DDFREQ ; Set cursor to "frequency".
call set_LCD ;
; *** Trim count data ***
MOV f CNT+0, w ; X <- Count value.
MOV wf X+0 ; Y <- 1000 / Resolution.
MOV f CNT+1, w ; X <- X / Y.
MOV wf X+1 ;
MOV f CNT+2, w ;
MOV wf X+2 ;
clrf X+3 ;
clrf EX+0 ;
clrf EX+1 ;
clrf EX+2 ;
clrf EX+3 ;
;
MOV lw 10 ;
MOV wf Y+0 ;
clrf Y+1 ;
clrf Y+2 ;
clrf Y+3 ;
;
MOV f RESMODE, w ;
sublw FRES_1000 ;
btfsc status, z ;
goto dpln_cv0 ;
;
MOV wf I ;
dpln_trim ;
call div_xy ;
;
decfsz I ;
goto dpln_trim ;
; *** Convert data to string ***
dpln_cv0
MOV f X+0, w ; Y <- X.
MOV wf Y+0 ; (Y: frequency in kHz)
MOV f X+1, w ;
MOV wf Y+1 ;
MOV f X+2, w ;
MOV wf Y+2 ;
MOV f X+3, w ;
MOV wf Y+3 ;
iorwf Y+2, w ; Display "Too Long !!"
iorwf Y+1, w ; if value = 0.
iorwf Y+0, w ; (Less than 1 kHz)
btfss status, z ;
goto dpln_cv1 ;
;
MOV lw s_over ;
MOV wf LCD_FXMPTR ;
call dsp_fixstr ;
goto end_dpln ;
dpln_cv1
MOV lw 00h ; X <- 300000000 / Y
MOV wf X+0 ; (X: wave length in mm)
MOV lw 0A3h ; & convert to string.
MOV wf X+1 ;
MOV lw 0E1h ;
MOV wf X+2 ;
MOV lw 11h ;
MOV wf X+3 ;
call div_xy ;
call x_to_str ;
; *** Display wave length ***
MOV lw 3 ; Set decimal point location.
MOV wf LCD_DPOINT ; (X.XXX m)
call dsp_value ; Display value.
end_dpln
MOV lw s_m ; Add unit. (m)
MOV wf LCD_FXMPTR ;
call dsp_fixstr ;
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; Display value. (With 0 suppless & decimal point)
; Input : LCD_STRBUF (String buffer)
; LCD_DPOINT (Decimal point from right side)
; Output: None.
; W, Index register & variable I will be broken.
;-------------------------------------------------------------------------
dsp_value
; *** Initialize ***
bsf LCD_RSEL, L_SELDR ; Select data register.
MOV lw LCD_STRBUF ; Set pointer of string.
MOV wf fsr ;
; *** Display sPACe (Zero suppless) ***
MOV lw MAXDIGIT-1 ; Set max space count.
MOV wf I ; (MAXDIGIT - 1)
dspvl_l1
MOV f I, w ; Exit this loop if
subwf LCD_DPOINT, w ; this loc. = decimal point or
btfsc status, z ; not zero.
goto dspvl_2s ;
;
MOV f indf, w ;
sublw ’0’ ;
btfss status, z ;
goto dspvl_2s ;
MOV lw ’ ’ ; Put ’ ’.
call set_LCD ;
incf fsr ; Set location to next.
decfsz I ;
goto dspvl_l1 ;
; *** Display number & decimal point ***
dspvl_2s
incf I ; Increment counter.
dspvl_l2
MOV f indf, w ; Display number.
call set_LCD ;
incf fsr ; Decrement counter &
decf I ; skip below if this loc
MOV f I, w ; is not decimal point loc.
subwf LCD_DPOINT, w ;
btfss status, z ;
goto dspvl_2e ;
MOV lw ’.’ ; Display decimal point.
call set_LCD ;
dspvl_2e
MOV f I, f ; Continue if I > 0.
btfss status, z ;
goto dspvl_l2 ;
; *** Return from subroutine ***
clrf LCD_RSEL ; Set to default.
return
;-------------------------------------------------------------------------
; Convert value of X to string. (Fixed 10 digits)
; Input : X[0]- X[3] (Value)
; EX[0]-EX[3]
; Output: LCD_STRBUF (Buffer of string for LCD)
; W, Index register & variable I, Y, EY will be broken.
;-------------------------------------------------------------------------
x_to_str
; *** Initialize ***
MOV lw LCD_STRBUF ; Set pointer of string.
addlw 9 ; (To bottom)
MOV wf fsr
MOV lw 10 ; Set loop counter &
MOV wf I ; Y.
MOV wf Y+0 ;
clrf Y+1 ;
clrf Y+2 ;
clrf Y+3 ;
; *** Conversion loop (32 bits = 10 digits max) ***
xts_loop
call div_xy ; X <- X / 10.
MOV f EY+0, w ; EY(Lowest digit) <- X mod 10.
addlw ’0’ ; Change to ASCII &
MOV wf indf ; store.
decf fsr ; Set location to next.
decfsz I ;
goto xts_loop ;
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; Clear screen. (display)
; Input : None.
; Output: None.
; W register & variable LCD_DATA will be broken.
;-------------------------------------------------------------------------
cls
; *** Clear display ***
MOV lw L_DSPCLR ; Clear display.
MOV wf LCD_DATA ;
call set_LCDcmd ;
MOV lw 5 ; Wait.
call wait_ms ;
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; Display fixed string. (ASCIZ string on ROM)
; Input : LCD_FXMPTR (Pointer of fixed ASCIZ string table)
; Output: None.
; W, Index register, variable & LCD_FXMPTR will be broken.
;-------------------------------------------------------------------------
dsp_fixstr
; *** Initialize ***
bsf LCD_RSEL, L_SELDR ; Select data register.
; *** Display loop ***
dfs_loop
call get_fixchr ; Exit if character = NULL.
addlw 0 ;
btfsc status, z ;
goto end_dfs ;
call set_LCD ; Display character.
incf LCD_FXMPTR ; Continue.
goto dfs_loop ;
; *** Return from subroutine ***
end_dfs
clrf LCD_RSEL ; Set to default.
return
;-------------------------------------------------------------------------
; Get character from fixed message table.
; Input : LCD_FXMPTR (Pointer of fixed ASCIZ string table)
; Output: None.
; W register will be broken.
;-------------------------------------------------------------------------
get_fixchr
MOV f LCD_FXMPTR, w ; Caution: Upper byte of PCL
MOV wf pcl ; is always 0.
;-------------------------------------------------------------------------
; Set LCD command for standard operation.
; Input : W register (Command)
; Output: None.
; W register & variable LCD_DATA will be broken.
;-------------------------------------------------------------------------
set_LCD
; *** Set command ***
MOV wf LCD_DATA
call set_LCDcmd
call wait_100us
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; Set LCD command (Instruction).
; Input : LCD_RSEL (LCD register select)
; LCD_DATA (LCD data)
; Output: Port A, Port B (Data output port for LCD)
; W register will be broken.
;-------------------------------------------------------------------------
set_LCDcmd
; *** Select register ***
bcf portb, LCD_RS ; Select register.
btfsc LCD_RSEL, L_SELDR ;
bsf portb, LCD_RS ;
; *** Send upper nibbles ***
MOV lw 11110000b ; Set upper nibbles.
andwf porta, f ;
swapf LCD_DATA, w ;
andlw 00001111b ;
iorwf porta, f ;
bsf portb, LCD_LE ; Strobe.
nop ;
nop ;
bcf portb, LCD_LE ;
nop ;
nop ;
; *** Send lower nibbles ***
MOV lw 11110000b ; Set lower nibbles.
andwf porta, f ;
MOV f LCD_DATA, w ;
andlw 00001111b ;
iorwf porta, f ;
bsf portb, LCD_LE ; Strobe.
nop ;
nop ;
bcf portb, LCD_LE ;
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; General: Add. (32 bits source + 32 bits destination)
; Input : X[0]-X[3] (Source : 32 bits)
; Y[0]-Y[3] (Destination: 32 bits)
; Output: X[0]-X[3] (Answer : 32 bits)
; W register will be broken.
;
; Allocations (MSB <-> LSB):
; X[3] X[2] X[1] X[0]
; Y[3] Y[2] Y[1] Y[0]
;-------------------------------------------------------------------------
add_xy
; *** Add Y to X ***
MOV f Y+0, w ; Lower.
addwf X+0, f ;
MOV lw 1 ;
btfsc status, c ;
addwf X+1, f ;
btfsc status, c ;
addwf X+2, f ;
btfsc status, c ;
addwf X+3, f ;
MOV f Y+1, w ; Middle lower.
addwf X+1, f ;
MOV lw 1 ;
btfsc status, c ;
addwf X+2, f ;
btfsc status, c ;
addwf X+3, f ;
MOV f Y+2, w ; Middle upper.
addwf X+2, f ;
MOV lw 1 ;
btfsc status, c ;
addwf X+3, f ;
MOV f Y+3, w ; Upper.
addwf X+3, f ;
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; General: Subtract. (32 bits source - 32 bits destination)
; Input : X[0]-X[3] (Source : 32 bits)
; Y[0]-Y[3] (Destination: 32 bits)
; Output: X[0]-X[3] (Answer : 32 bits)
; W register will be broken.
;
; Allocations (MSB <-> LSB):
; X[3] X[2] X[1] X[0]
; Y[3] Y[2] Y[1] Y[0]
;-------------------------------------------------------------------------
sub_xy
; *** Subtract Y from X ***
MOV f Y+0, w ; Lower.
subwf X+0, f ;
MOV lw 1 ;
btfss status, c ; <- Positive if CF = 1.
subwf X+1, f ;
btfss status, c ;
subwf X+2, f ;
btfss status, c ;
subwf X+3, f ;
MOV f Y+1, w ; Middle lower.
subwf X+1, f ;
MOV lw 1 ;
btfss status, c ;
subwf X+2, f ;
btfss status, c ;
subwf X+3, f ;
MOV f Y+2, w ; Middle upper.
subwf X+2, f ;
MOV lw 1 ;
btfss status, c ;
subwf X+3, f ;
MOV f Y+3, w ; Upper.
subwf X+3, f ;
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; General: Multiply. (32 by 32 bits)
; Input : X[0]- X[3] (Source : 32 bits)
; Y[0]- Y[3] (Destination: 32 bits)
; Output: EX[0]-EX[3] (Answer : 64 bits)
; X[0]- X[3]
; EY[0]-EY[3] (As same as X[0]-X[3])
;
; W register will be broken.
;
; Notes: Referred to AKIZUKI’s PIC sample software.
; This routine uses the same technic of manual-calculation.
;
; Example: 00010010 (12h)
; x00110100 (34h)
; ----------
; 00000000
; 00000000
; 00010010
; 00000000
; 00010010
; 00010010
; 00000000
; 00000000
; ------------------
; 0000001110101000 (03A8h)
;
; Allocations (MSB <-> LSB):
; EX[3] EX[2] EX[1] EX[0] X[3] X[2] X[1] X[0]
; EY[3] EY[2] EY[1] EY[0] Y[3] Y[2] Y[1] Y[0]
;-------------------------------------------------------------------------
mul_xy
; *** Initialize ***
MOV f X+0, w ; EY <- X.
MOV wf EY+0 ;
MOV f X+1, w ;
MOV wf EY+1 ;
MOV f X+2, w ;
MOV wf EY+2 ;
MOV f X+3, w ;
MOV wf EY+3 ;
MOV f Y+0, w ; X <- Y.
MOV wf X+0 ;
MOV f Y+1, w ;
MOV wf X+1 ;
MOV f Y+2, w ;
MOV wf X+2 ;
MOV f Y+3, w ;
MOV wf X+3 ;
clrf EX+0 ; Clear EX.
clrf EX+1 ;
clrf EX+2 ;
clrf EX+3 ;
MOV lw 32 ; Set data length.
MOV wf MDLOOPCT ;
; *** Multiply loop (32 times) ***
mul_loop
btfss X+0, 0 ; Skip below if LSB of XL = ’0’.
goto mul_next ; (EY * ’0’ = 0)
bcf X+0, 0 ; Clear always LSB of X.
MOV f EY+0, w ; EX <- EX + EY.
addwf EX+0, f ;
MOV lw 1 ; Set LSB of X to ’1’
btfsc status, c ; if overflow. (Set carry)
addwf EX+1, f ;
btfsc status, c ;
addwf EX+2, f ;
btfsc status, c ;
addwf EX+3, f ;
btfsc status, c ;
bsf X+0, 0 ;
;
MOV f EY+1, w ;
addwf EX+1, f ;
MOV lw 1 ;
btfsc status, c ;
addwf EX+2, f ;
btfsc status, c ;
addwf EX+3, f ;
btfsc status, c ;
bsf X+0, 0 ;
;
MOV f EY+2, w ;
addwf EX+2, f ;
MOV lw 1 ;
btfsc status, c ;
addwf EX+3, f ;
btfsc status, c ;
bsf X+0, 0 ;
;
MOV f EY+3, w ;
addwf EX+3, f ;
btfsc status, c ;
bsf X+0, 0 ;
mul_next
bcf status, c ; Rotate EX + X to right.
rrf EX+3 ; (LSB of X -> MSB of EX)
rrf EX+2 ;
rrf EX+1 ;
rrf EX+0 ;
rrf X+3 ;
rrf X+2 ;
rrf X+1 ;
rrf X+0 ;
btfsc status, c ;
bsf EX+3, 7 ;
decfsz MDLOOPCT, f ; Continue if loop > 0.
goto mul_loop ;
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; General: Divide. (64 bits source by 32 bits destination)
; Input : EX[0]-EX[3] (Source : 64 bits)
; X[0]- X[3]
; Y[0]- Y[3] (Destination: 32 bits)
; Output: EX[0]-EX[3] (Answer : 64 bits)
; X[0]- X[3]
; Y[0]- Y[3] (Mod : 32 bits)
;
; W register will be broken.
;
; Notes: Referred to AKIZUKI’s PIC sample software.
; This routine uses the same technic of manual-calculation.
;
; Example: 0000000001100100 (64h)
; +------------------
; (10h) 1010| 0000001111101000 (03E8h)
; 1010
; -------------------
; 1011
; 1010
; -------------------
; 1010
; 1010
; -------------------
; 0
;
; Allocations (MSB <-> LSB):
; EX[3] EX[2] EX[1] EX[0] X[3] X[2] X[1] X[0]
; EY[3] EY[2] EY[1] EY[0] Y[3] Y[2] Y[1] Y[0]
;-------------------------------------------------------------------------
div_xy
; *** Initialize ***
clrf CALCTMP1+0 ; Clear temporary buffer.
clrf CALCTMP1+1 ;
clrf CALCTMP1+2 ;
clrf CALCTMP1+3 ;
clrf CALCTMP1+4 ;
MOV lw 64 ; Set data length.
MOV wf MDLOOPCT ;
; *** Divide loop (64 times) ***
div_loop
bcf status, c ; Shift CALCTMP1(Mod) + EX + X
rlf X+0 ; to left.
rlf X+1 ;
rlf X+2 ;
rlf X+3 ;
rlf EX+0 ;
rlf EX+1 ;
rlf EX+2 ;
rlf EX+3 ;
rlf CALCTMP1+0 ;
rlf CALCTMP1+1 ;
rlf CALCTMP1+2 ;
rlf CALCTMP1+3 ;
rlf CALCTMP1+4 ;
MOV f CALCTMP1+0, w ; CALCTMP2(Work) <- CALCTMP1.
MOV wf CALCTMP2+0 ;
MOV f CALCTMP1+1, w ;
MOV wf CALCTMP2+1 ;
MOV f CALCTMP1+2, w ;
MOV wf CALCTMP2+2 ;
MOV f CALCTMP1+3, w ;
MOV wf CALCTMP2+3 ;
MOV f CALCTMP1+4, w ;
MOV wf CALCTMP2+4 ;
MOV f Y+0, w ; CALCTMP2 <- CALCTMP2 - Y.
subwf CALCTMP2+0, f ; (Signed operation)
MOV lw 1 ;
btfss status, c ; <- Positive if CF=1.
subwf CALCTMP2+1, f ;
btfss status, c ;
subwf CALCTMP2+2, f ;
btfss status, c ;
subwf CALCTMP2+3, f ;
btfss status, c ;
subwf CALCTMP2+4, f ;
;
MOV f Y+1, w ;
subwf CALCTMP2+1, f ;
MOV lw 1 ;
btfss status, c ;
subwf CALCTMP2+2, f ;
btfss status, c ;
subwf CALCTMP2+3, f ;
btfss status, c ;
subwf CALCTMP2+4, f ;
;
MOV f Y+2, w ;
subwf CALCTMP2+2, f ;
MOV lw 1 ;
btfss status, c ;
subwf CALCTMP2+3, f ;
btfss status, c ;
subwf CALCTMP2+4, f ;
;
MOV f Y+3, w ;
subwf CALCTMP2+3, f ;
MOV lw 1 ;
btfss status, c ;
subwf CALCTMP2+4, f ;
btfsc CALCTMP2+4, 7 ; Skip below if CALCTMP2 < 0.
goto div_next ; (MSB of CALCTMP2 is ’1’)
MOV f CALCTMP2+0, w ; CALCTMP1(Mod) <- CALCTMP2 &
MOV wf CALCTMP1+0 ; LSB of X <- ’1’.
MOV f CALCTMP2+1, w ;
MOV wf CALCTMP1+1 ;
MOV f CALCTMP2+2, w ;
MOV wf CALCTMP1+2 ;
MOV f CALCTMP2+3, w ;
MOV wf CALCTMP1+3 ;
MOV f CALCTMP2+4, w ;
MOV wf CALCTMP1+4 ;
;
bsf X+0, 0 ;
div_next
decfsz MDLOOPCT, f ; Continue if loop > 0.
goto div_loop ;
; *** Return from subroutine ***
MOV f CALCTMP1+0, w ; EY(Mod) <- CALCTMP1.
MOV wf EY+0 ;
MOV f CALCTMP1+1, w ;
MOV wf EY+1 ;
MOV f CALCTMP1+2, w ;
MOV wf EY+2 ;
MOV f CALCTMP1+3, w ;
MOV wf EY+3 ;
return
;-------------------------------------------------------------------------
; General: Rotate left. (16 bits length)
; Input : W (Pointer of entry)
;-------------------------------------------------------------------------
rl16
; *** Rotate left ***
MOV wf fsr
bcf status, c ; Set ’0’ on LSB.
rlf indf, f ; Lower.
incf fsr, f
rlf indf, f ; Upper.
decf fsr, f
btfsc status, c
bsf indf, 0 ; Set ’1’ on LSB if CF = ’1’.
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; General: Rotate right. (16 bits length)
; Input : W (Pointer of entry)
;-------------------------------------------------------------------------
rr16
; *** Rotate right ***
MOV wf fsr
incf fsr, f
bcf status, c ; Set ’0’ on MSB.
rrf indf, f ; Upper.
decf fsr, f
rrf indf, f ; Lower.
incf fsr, f
btfsc status, c
bsf indf, 7 ; Set ’1’ on MSB if CF = ’1’.
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; General: Rotate left. (32 bits length)
; Input : W (Pointer of entry)
;-------------------------------------------------------------------------
rl32
; *** Rotate left ***
MOV wf fsr
bcf status, c ; Set ’0’ on LSB.
rlf indf, f ; Lower.
incf fsr, f
rlf indf, f ; Middle lower.
incf fsr, f
rlf indf, f ; Middle upper.
incf fsr, f
rlf indf, f ; Upper.
decf fsr, f
decf fsr, f
decf fsr, f
btfsc status, c
bsf indf, 0 ; Set ’1’ on LSB if CF = ’1’.
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; General: Rotate right. (32 bits length)
; Input : W (Pointer of entry)
;-------------------------------------------------------------------------
rr32
; *** Rotate right ***
MOV wf fsr
incf fsr, f
incf fsr, f
incf fsr, f
bcf status, c ; Set ’0’ on MSB.
rrf indf, f ; Upper.
decf fsr, f
rrf indf, f ; Middle upper.
decf fsr, f
rrf indf, f ; Middle lower.
decf fsr, f
rrf indf, f ; Lower.
incf fsr, f
incf fsr, f
incf fsr, f
btfsc status, c
bsf indf, 7 ; Set ’1’ on MSB if CF = ’1’.
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; General: shift left. (16 bits length)
; Input : W (Pointer of entry)
;-------------------------------------------------------------------------
sl16
; *** Shift left ***
MOV wf fsr
bcf status, c ; Set ’0’ on LSB.
rlf indf, f ; Lower.
incf fsr, f
rlf indf, f ; Upper.
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; General: Shift right. (16 bits length)
; Input : W (Pointer of entry)
;-------------------------------------------------------------------------
sr16
; *** Shift right ***
MOV wf fsr
incf fsr, f
bcf status, c ; Set ’0’ on MSB.
rrf indf, f ; Upper.
decf fsr, f
rrf indf, f ; Lower.
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; General: Shift left. (32 bits length)
; Input : W (Pointer of entry)
;-------------------------------------------------------------------------
sl32
; *** Shift left ***
MOV wf fsr
bcf status, c ; Set ’0’ on LSB.
rlf indf, f ; Lower.
incf fsr, f
rlf indf, f ; Middle lower.
incf fsr, f
rlf indf, f ; Middle upper.
incf fsr, f
rlf indf, f ; Upper.
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; General: Shift right. (32 bits length)
; Input : W (Pointer of entry)
;-------------------------------------------------------------------------
sr32
; *** Shift right ***
MOV wf fsr
incf fsr, f
incf fsr, f
incf fsr, f
bcf status, c ; Set ’0’ on MSB.
rrf indf, f ; Upper.
decf fsr, f
rrf indf, f ; Middle upper.
decf fsr, f
rrf indf, f ; Middle lower.
decf fsr, f
rrf indf, f ; Lower.
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; General: Wait procedure.
; Input : W (Time in milliseconds)
; Output: None.
; W register & variable WAIT1, WAIT2 will be broken.
;-------------------------------------------------------------------------
wait_ms
; *** Wait loop ***
MOV wf WAIT1 ; Set milliseconds loop counter.
wm_loop1
MOV lw 249 ; Set microseconds loop counter.
MOV wf WAIT2 ; (996 microseconds / 4)
wm_loop2
nop
nop
nop
nop
nop
nop
nop
decfsz WAIT2 ; Continue if loop2 > 0.
goto wm_loop2 ;
nop
nop
nop
nop
nop
nop
decfsz WAIT1 ; Continue if loop1 > 0.
goto wm_loop1 ;
; *** Return from subroutine ***
return
;-------------------------------------------------------------------------
; General: Wait procedure. (Fixed 100 microseconds)
; Input : None.
; Output: None.
; W register & variable WAIT1 will be broken.
;-------------------------------------------------------------------------
wait_100us
; *** Wait loop ***
MOV lw 48 ; Set 100 microseconds loop counter.
MOV wf WAIT1 ; (96 microseconds)
wu_loop
nop
nop
decfsz WAIT1 ; Continue if loop > 0.
goto wu_loop ;
; *** Return from subroutine ***
nop
nop
nop
nop
nop
return
; End of COUNTER.ASM
16f84_32.H
上一篇:485通讯PIC源程序
下一篇:p18f458单片机通讯程序
推荐阅读最新更新时间:2024-03-16 15:48
设计资源 培训 开发板 精华推荐
- 柔灵科技陈涵:将小型、柔性的脑机接口睡眠设备,做到千家万户
- 微灵医疗李骁健:脑机接口技术正在开启意识与AI融合的新纪元
- USB Type-C® 和 USB Power Delivery:专为扩展功率范围和电池供电型系统而设计
- 景昱医疗耿东:脑机接口DBS治疗技术已实现国产替代
- 首都医科大学王长明:针对癫痫的数字疗法已进入使用阶段
- 非常见问题解答第223期:如何在没有软启动方程的情况下测量和确定软启动时序?
- 兆易创新GD25/55全系列车规级SPI NOR Flash荣获ISO 26262 ASIL D功能安全认证证书
- 新型IsoVu™ 隔离电流探头:为电流测量带来全新维度
- 英飞凌推出简化电机控制开发的ModusToolbox™电机套件
- 意法半导体IO-Link执行器电路板为工业监控和设备厂商带来一站式参考设计