alamy said:meaning that , i can have time delay up to 30 minutes just using PIC..how many loop should i put in my code?...
what is the maximum time delay....taht PIc can do?...
how do i implement these loops (long range time delay)...
; Delay = 300 seconds
; Clock frequency = 4 MHz
; Actual delay = 300 seconds = 300000000 cycles
; Error = 0 %
cblock
d1
d2
d3
d4
endc
;299999995 cycles
movlw 0x54
movwf d1
movlw 0xA1
movwf d2
movlw 0xFD
movwf d3
movlw 0x02
movwf d4
Delay_0
decfsz d1, f
goto $+2
decfsz d2, f
goto $+2
decfsz d3, f
goto $+2
decfsz d4, f
goto Delay_0
;5 cycles
goto $+1
goto $+1
nop
alamy said:thanks a lot Nigel...
ok...
for the time delay...can i use RETLW to call my subroutine?
which is
retlw 5minutes
retlw 15minutes
retlw 30minutes....
and so on...
actually i do develop lookup table which have 64 values (size)i.e. 6 bits inputs...
i want my PIC have a time delay for the given inputs (6 bits)...
instead of using retlw (if can)...is there any alternative way to put my pic working as using retlw...
thank you..
With a table you can either have a table of RETLW, which returns a corresponding value (lookup table), or a table of GOTO, which is a jump table. You can't use a table of CALL, because it will RETURN to the section of the table it came from, and execute all subroutines below in the table
;***** VARIABLE DEFINITIONS
STATUS EQU 03h ; variable used for context saving
TRISA EQU 85h ; variable used for context saving
PORTA EQU 05H
TRISB EQU 86h
PORTB EQU 06h
;**********************************************************************
ORG 0x000 ; processor reset vector
goto main ; go to beginning of program
ORG 0x004 ; interrupt vector location
main bsf STATUS,5 ; bank 0 -----> bank 1
movlw b'00000000' ; set the port a as outputs
movwf TRISA ;
movlw b'00111111' ; set the port b as inputs
movwf TRISB
bcf STATUS,5 ; bank 1 -----> bank 0
read movf PORTB,w ; read input from port B
andlw b'00111111' ; mask of bits
call table ; refer to table, compare with inputs
movwf PORTA ; write to outputs
goto read ; re-read the status of inputs
table addwf PCL,f ; inputs outputs
retlw b'0001' ; 0 off
retlw b'0001' ; 1 off
retlw b'0001' ; 2 off
retlw b'0001' ; 3 off
retlw b'0001' ; 4 off
retlw b'0001' ; 5 off
retlw b'0001' ; 6 off
retlw b'0001' ; 7 off
retlw b'0001' ; 8 off
retlw b'0001' ; 9 off
retlw b'0001' ; 10 off
retlw b'0001' ; 11 off
retlw b'0001' ; 12 off
retlw b'0001' ; 13 off
retlw b'0001' ; 14 off
retlw b'0001' ; 15 off
retlw b'0001' ; 16 off
retlw b'0001' ; 17 off
retlw b'0001' ; 18 off
retlw b'0001' ; 19 off
retlw b'0010' ; 20 low
retlw b'0010' ; 21 low
retlw b'0010' ; 22 low
retlw b'0010' ; 23 low
retlw b'0001' ; 24 off
retlw b'0001' ; 25 off
retlw b'0001' ; 26 off
retlw b'0001' ; 27 off
retlw b'0100' ; 28 med
retlw b'0100' ; 26 med
retlw b'0100' ; 30 med
retlw b'0100' ; 31 med
retlw b'0100' ; 32 med
retlw b'0100' ; 33 med
retlw b'0100' ; 34 med
retlw b'1000' ; 35 high
retlw b'1000' ; 36 high
retlw b'1000' ; 37 high
retlw b'1000' ; 38 high
retlw b'1000' ; 39 high
retlw b'0100' ; 40 med
retlw b'0100' ; 41 med
retlw b'0100' ; 42 med
retlw b'0100' ; 43 med
retlw b'0100' ; 44 med
retlw b'1000' ; 45 high
retlw b'1000' ; 46 high
retlw b'1000' ; 47 high
retlw b'0100' ; 48 med
retlw b'0100' ; 49 med
retlw b'0100' ; 50 med
retlw b'1000' ; 51 high
retlw b'1000' ; 52 high
retlw b'1000' ; 53 high
retlw b'1000' ; 54 high
retlw b'1000' ; 55 high
retlw b'0100' ; 56 med
retlw b'0100' ; 57 med
retlw b'0100' ; 58 med
retlw b'1000' ; 59 high
retlw b'1000' ; 60 high
retlw b'1000' ; 61 high
retlw b'1000' ; 62 high
retlw b'1000' ; 63 high
END ; directive 'end of program'
retlw b'0001' ; 0 off
goto ShortDel
read movf PORTB,w ; read input from port B
andlw b'00111111' ; mask of bits
call table ; refer to table, compare with inputs
call DelayW ; delay W number of times
movwf PORTA ; write to outputs
goto read ; re-read the status of inputs
DelayW movwf count1
d1 movlw 0xC7 ;delay 1mS
movwf counta
movlw 0x01
movwf countb
Delay_0
decfsz counta, f
goto $+2
decfsz countb, f
goto Delay_0
decfsz count1 ,f
goto d1
retlw 0x00
You simply need to call a routine which delays a certain time, multiplied by the value of W. So if the delay time is 1 second, calling it with 1 in W delays 1 second, calling it with 64 would delay 64 seconds.
You can modify your routine like this.
Code:
read movf PORTB,w ; read input from port B
andlw b'00111111' ; mask of bits
call table ; refer to table, compare with inputs
call DelayW ; delay W number of times
movwf PORTA ; write to outputs
goto read ; re-read the status of inputs
read movf PORTB,w ; read input from port B
andlw b'00111111' ; mask of bits
call table ; refer to table, compare with inputs
call Delay5 ; 5 minutes delay
movwf PORTA ; write to outputs
goto read ; re-read the status of inputs
Obviously you also need to rewrite the table, so it gives the time delay values you require
table addwf PCL,f ; inputs outputs
retlw Delay5
retlw Delay10
retlw Delay5
: :
: :
retlw Delay30
retlw Delay5
retlw Delay5
; Delay = 300 seconds
; Clock frequency = 4 MHz
; Actual delay = 300 seconds = 300000000 cycles
; Error = 0 %
cblock
d1
d2
d3
d4
endc
;299999995 cycles
movlw 0x54
movwf d1
movlw 0xA1
movwf d2
movlw 0xFD
movwf d3
movlw 0x02
movwf d4
Delay_0
decfsz d1, f
goto $+2
decfsz d2, f
goto $+2
decfsz d3, f
goto $+2
decfsz d4, f
goto Delay_0
;5 cycles
goto $+1
goto $+1
nop
; Delay = 300 seconds
; Clock frequency = 4 MHz
; Actual delay = 300 seconds = 300000000 cycles
; Error = 0 %
cblock
d1
d2
d3
d4
count1
endc
DelayW movwf count1
Delay5
;299999995 cycles
movlw 0x54
movwf d1
movlw 0xA1
movwf d2
movlw 0xFD
movwf d3
movlw 0x02
movwf d4
Delay_0
decfsz d1, f
goto $+2
decfsz d2, f
goto $+2
decfsz d3, f
goto $+2
decfsz d4, f
goto Delay_0
;5 cycles
goto $+1
goto $+1
nop
decfsz count1 ,f
goto Delay5
retlw 0x00
If you 'call DelayW' with 1 in W, it will delay 5 minutes, if you call it with 2 in W it will delay 10 minutes, and so on. You 64 word long table just needs to return the required value in W.
table addwf PCL,f
retlw 1 ; 5 minutes delay
retlw 2 ; 10 minutes delay
retlw 3 ; 30 minutes delay
: :
: :
retlw 3
retlw 3
retlw 1
table addwf PCL,f
retlw Delay5
retlw Delay10
retlw Delay5
: :
: :
retlw Delay30
retlw Delay5
retlw Delay5
alamy said:i do understand to implement 'variable' time delay...by using 1 subroutine i can have up to 255 time delay (for my case), just modify my 'multiply' valeu in my table...
let say...for the given input, my pic will ON for 5 minutes, and for another inputs, my pic will OFF for 15 minutes...how do i modified my table...using modified code given?..
maybe i can have 2 preset delay ...1 for on ...1 for off...what do you think?..
call TurnON
movlw 1 ;set 5 minute delay
call table
call DelayW
call TurnOFF
movlw 3 ;set 15 minute delay
call DelayW
goto Main ;loop back to main loop
read movf PORTB,w ; read input from port B
andlw b'00111111' ; mask of bits
call table ; refer to table, compare with inputs
call DelayW ; delay W number of times
table addwf PCL,f
retlw 1 ; 5 minutes delay, off
retlw 2 ; 10 minutes delay, off
retlw 3 ; 15 minutes delay,
: :
: :
retlw 6 ; ON for 30 minutes
retlw 3 ; ON for 15 minutes
retlw 1 ; ON for 5 minutes
; Delay = 300 seconds
; Clock frequency = 4 MHz
; Actual delay = 300 seconds = 300000000 cycles
; Error = 0 %
cblock
d1
d2
d3
d4
count1
endc
DelayW
movwf count1
Delay5 ;299999995 cycles
movlw 0x54
movwf d1
movlw 0xA1
movwf d2
movlw 0xFD
movwf d3
movlw 0x02
movwf d4
Delay_0
decfsz d1, f
goto $+2
decfsz d2, f
goto $+2
decfsz d3, f
goto $+2
decfsz d4, f
goto Delay_0 ;5 cycles
goto $+1
goto $+1
nop
decfsz count1 ,f
goto Delay5
retlw 0x00
alamy said:My system have 6 inputs and 1 output (on-off) …variable time delays.
My pic have the 64 possibilities input value which produce 6 or more type of output that is time delay for ON (5,15,30 minutes) and also time delay for OFF (5,15,30 minutes). For input range (possibilities value) 0-32 …my pic will OFF with certain period (5,15,30 minutes) and 33-63 it will ON (5,15,30 minutes) .
My program flow will be like this:--
then for the read routine :
Code:read movf PORTB,w ; read input from port B andlw b'00111111' ; mask of bits call table ; refer to table, compare with inputs call DelayW ; delay W number of times
movwf Temp
;***** VARIABLE DEFINITIONS
STATUS EQU 03h ; variable used for context saving
TRISA EQU 85h ; variable used for context saving
PORTA EQU 05H
TRISB EQU 86h
PORTB EQU 06h
;**********************************************************************
ORG 0x000 ; processor reset vector
goto main ; go to beginning of program
ORG 0x004 ; interrupt vector location
main bsf STATUS,5 ; bank 0 -----> bank 1
movlw b'00000000' ; set the port a as outputs
movwf TRISA ;
movlw b'00111111' ; set the port b as inputs
movwf TRISB
bcf STATUS,5 ; bank 1 -----> bank 0
williB said:alamy Can you use two ' ORG ' statements like that..??
how is the assembler going to handle two ORG statements?
this is the code...i have never tried it though..
Code:ORG 0x000 ; processor reset vector goto main ; go to beginning of program ORG 0x004 ; interrupt vector location main bsf STATUS,5 ; bank 0 -----> bank 1
ORG 0x000 ; processor reset vector
goto main ; go to beginning of program
ORG 0x004 ; interrupt vector location
RETFIE ; return from interrupt (just in case!)
; main now at 0x0005
main bsf STATUS,5 ; bank 0 -----> bank 1
You can then check bit 5 to see if it's '1' or not, and the program can branch accordingly - to routines to either turn ON or turn OFF then delay the amount of time set.
Read Movf PORTB,w
Subwf SP,w ; where SP define as 31 (b’11111’)
Btfss STATUS,C ; I’m not sure use this one….
Call TurnOn
Call TurnOff
TurnOn andlw b’00011111’
Call TableOn
Call DelayW
Bcf PORTA
Goto Read
TurnOff andlw b’00011111’
Call TableOff
Call DelayW
Bsf PORTA
Goto Read
TableOn Addwf pcl,f
Retlw 1
Retlw 1
Retlw 2
Retlw 1
Retlw 3
:
:
Retlw 1
TableOff Addwf pcl,f
Retlw 1
Retlw 1
Retlw 2
Retlw 1
Retlw 3
:
:
Retlw 1
Delay = 300 seconds
; Clock frequency = 4 MHz
; Actual delay = 300 seconds = 300000000 cycles
; Error = 0 %
cblock
d1
d2
d3
d4
count1
endc
DelayW movwf count1
Delay5
;299999995 cycles
movlw 0x54
movwf d1
movlw 0xA1
movwf d2
movlw 0xFD
movwf d3
movlw 0x02
movwf d4
Delay_0
decfsz d1, f
goto $+2
decfsz d2, f
goto $+2
decfsz d3, f
goto $+2
decfsz d4, f
goto Delay_0
;5 cycles
goto $+1
goto $+1
nop
decfsz count1 ,f
goto Delay5
retlw 0x00
Another way of doing it, would be to use the full 64 byte table, but for the second half of the table have bit 7 set in the entries, then after reading the table test bit 7, and turn On or OFF accordingly - remembering to mask off bit 7 before calling the delay
We use cookies and similar technologies for the following purposes:
Do you accept cookies and these technologies?
We use cookies and similar technologies for the following purposes:
Do you accept cookies and these technologies?