Continue to Site

Welcome to EDAboard.com

Welcome to our site! EDAboard.com is an international Electronics Discussion Forum focused on EDA software, circuits, schematics, books, theory, papers, asic, pld, 8051, DSP, Network, RF, Analog Design, PCB, Service Manuals... and a whole lot more! To participate you need to register. Registration is free. Click here to register now.

Write Delay Function using Assembly Language in PIC16F84

Status
Not open for further replies.

cadvis

Junior Member level 1
Joined
Jun 11, 2008
Messages
17
Helped
0
Reputation
0
Reaction score
0
Trophy points
1,281
Activity points
1,479
If 4Mhz Oscillator is used with PIC16F84 then Cycle of Pic would be 1,000,000 or 1 Mhz. If presacler of 256 is used then it comes 3906.25 cycle per second. How could i acomodate it in my programming code as max no for one byte is 255.

I also used Delay Calculator to generate code but its also not working

Regards
 

you can use oscillator like 20MHz? then it is easier to manipulate it
 

What size delay are you looking for?

And how accurate must it be?

---------- Post added at 11:15 ---------- Previous post was at 10:45 ----------

Code:
Delay500u
	nop
        goto	$+1
	Movlw	D'164'	
	Movwf	Delay
delay500u_loop
	Decfsz	Delay,f
	goto 	delay500u_loop
	return

This generates 500us delay using a 4Mhz, the delay starts with the call command and finishes with the return command, so the line calling the delay is included in the delay. This routine is not dependant on the PreScaler settings, because it does not use TMR0.

You do not say if the delay is to be used via an interrupt or via a call to stop everything while it is executing.
 
Last edited:

hi,

i am looking for 5 second delay. Can you explain how $+1 works.

Thanks for your support and time.

regards
 

basically goto +$, jumps to the next instruction but uses 2 clock cycles and only 1 memory location.

How critical is the 5 sec delay?
 
Last edited:

hi,

i am looking for 5 second delay. Can you explain how $+1 works.

Thanks for your support and time.

regards



Hi,

Th $+1 simply means goto the next instruction; the program counter plus 1.

It seems a bit pointless in the way its used here, the only reason is that a Nop instruction takes 1 machine cycle whereas a Goto takes 2, its often used in loops to make the timing exact.


You did not actually answer the easlier question of if you are trying to do a delay working on the Timers in conjuntion with the Interrupts, which alllows your program to do other things while the delay is timing out, or to use the simpler dedicated program loop delay.

Would suggest for a beginner and a 5 second delay you use the latter loop delay which is just an extended version of the 500us delay.

You said in your first post you used a delay calculator but it did not work ? - if you post the code you used perhaps we can see where you have gone wrong.

Code:
; Delay = 5 seconds
; Clock frequency = 4 MHz

; Actual delay = 5 seconds = 5000000 cycles
; Error = 0 %

	cblock
	d1
	d2
	d3
	endc

			;5000000 cycles
	movlw	0x2D
	movwf	d1
	movlw	0xE7
	movwf	d2
	movlw	0x0B
	movwf	d3
Delay_0
	decfsz	d1, f
	goto	$+2
	decfsz	d2, f
	goto	$+2
	decfsz	d3, f
	goto	Delay_0

; Generated by http://www.golovchenko.org/cgi-bin/delay (December 7, 2005 version)
; Wed Dec 15 18:17:18 2010 GMT

; See also various delay routines at http://www.piclist.com/techref/microchip/delays.htm
 

Hi,

Th $+1 simply means goto the next instruction; the program counter plus 1.

It seems a bit pointless in the way its used here, the only reason is that a Nop instruction takes 1 machine cycle whereas a Goto takes 2, its often used in loops to make the timing exact.


Hi the only reason it is there is to reduce the amount of memory used I pulled it from some my code where space was tight and I needed to keep down, As WP100 says that and the nop just ensure that the complete routine from Including the call and return take exactly 500 cycles ie 500us. I could have made it 3 x nop commands
 

Hi,
This code is generated from Piclist - Microchip PIC Delay Code Generator -
Code:
; Delay = 5 seconds
; Clock frequency = 4 MHz

; Actual delay = 5 seconds = 5000000 cycles
; Error = 0 %

Delay
			;4999993 cycles
	movlw	0x2C
	movwf	d1
	movlw	0xE7
	movwf	d2
	movlw	0x0B
	movwf	d3
Delay_0
	decfsz	d1, f
	goto	$+2
	decfsz	d2, f
	goto	$+2
	decfsz	d3, f
	goto	Delay_0

			;3 cycles
	goto	$+1
	nop

			;4 cycles (including call)
	return

The subroutine should be called as below:
Code:
list P=16F84A
#include "p16f84a.inc"
__config 0x3ff1 ; or any value that you set

	cblock 0x0c
	d1
	d2
	d3
	endc

        org 0x00
        goto start

start
;.......................
;.......................
;.......................
; Your code here

call Delay ;Calling the subroutine when you need the 5 second delay

;.......................
;Remainder of code

end

goto $+n means go n instructions forward from current instruction
goto $-n means go n instructions backward from current instruction

eg
Code:
here goto $+2
next goto $-1
now goto goto $+1
then goto $-2
Here, the program first goes from "here" 2 instructions further to "now", then 1 instruction to "then", then 2 instructions back to "next", then 1 instruction back to "here", then repeating the loop.

Hope I could make things clear.
Hope this helps.
Tahmid.

---------- Post added at 14:48 ---------- Previous post was at 14:46 ----------

$ indicates current instruction, ie instruction currently being processed by the microcontroller
 

    V

    Points: 2
    Helpful Answer Positive Rating
I am using it to simulate led on and for 5 sec respectively. Using Real Pic Simulator to simulate it

Here is the code. I finding difficulties while simulating. Does any one check ot on simulator and send me that file to verify it.

regards


;---------------------------------------------------------------------------------------------------
;EQUATES

TRM0 equ 01h ;Address of TIMER0. It runs at 1/4 of
;clock speed. If clock is of 32,768 HZ
;then it is 8,192 pulses per second.
STATUS equ 03h ;Address of Status Register.
PORTA equ 05h ;Adress of PORTA.
TRISA equ 85h ;Address of TRISA.To Designate I\O
;of PORTA. Specify Which Port is
;input or output.
OPTION_R equ 81h ;Address of Option Register. IT is used to
;reduce the pulse rate by factor 2, 4,8,....
; 256. here 256 is used.
COUNT equ 08h
cblock 0x0c
d1
d2
d3
endc
;---------------------------------------------------------------------------------------------------
bsf 03h,5 ; Moving from 'Bank 0' to 'Bank 1'.
movlw b'00000' ; Move adress 00000 to 'w' register .
movwf 85h ; move value of W into TRISA. It designate all bits as
;output

bcf 03h,5 ; Move back to 'Bank 0'.


;---------------------------------------------------------------------------------------------------
start
movlw b'00001' ; means 2 in decimal, 00010 in decimal. logic 1 to 2nd bit.
movwf 05h ; move logic 1 to 2nd Bit of PORTA. It let to on LED connected to 2nd bit i.s A1.

call Delay ;Call delay function
call Delay_0
movlw 00h ; to send 0 at w.
movwf 05h ; to get off lED.

call Delay
call Delay_0 ; call delay function.
;---------------------------------------------------------------------------------------------------

;4999993 cycles
Delay movlw 0x2C
movwf d1
movlw 0xE7
movwf d2
movlw 0x0B
movwf d3
Delay_0
decfsz d1, f
goto $+2
decfsz d2, f
goto $+2
decfsz d3, f
goto Delay_0

;3 cycles
goto $+1
nop

;4 cycles (including call)
return
;---------------------------------------------------------------------------------------------------
end
 

Hi,

Well you are very nearly there, couple of things causing it not to run.

Always specify the processor type using List and Include
The "Delay" is one complete subroutine, you do not need to call Delay_0
After you have called the second delay you have not put a Goto to send the code back to the 'start' of your program loop.

I have just used MPlabs SIMulator -it checks the delay timing and shows the Ports condition -see pic.

While you code will now work, the way you are coding will make things difficult - will send some code of the same thing showing how much easier it is to use register Labels / Names




Code:
	LIST P=16f84
	
	#INCLUDE"P16f84.INC"


	;---------------------------------------------------------------------------------------------------
	;EQUATES
	
TRM0 equ 01h 			;Address of TIMER0. It runs at 1/4 of
						;clock speed. If clock is of 32,768 HZ
						;then it is 8,192 pulses per second.
STATUS equ 03h			 ;Address of Status Register.
PORTA equ 05h 			;Adress of PORTA.
TRISA equ 85h 			;Address of TRISA.To Designate I\O
						;of PORTA. Specify Which Port is
						;input or output.
OPTION_R equ 81h 		;Address of Option Register. IT is used to
						;reduce the pulse rate by factor 2, 4,8,....
						; 256. here 256 is used.
COUNT equ 08h

	cblock 0x0c
	d1
	d2
	d3
	endc
	;---------------------------------------------------------------------------------------------------
	bsf 03h,5 			; Moving from 'Bank 0' to 'Bank 1'.
	movlw b'00000' 		; Move adress 00000 to 'w' register .
	movwf 85h 			; move value of W into TRISA. It designate all bits as
						;output
	
	bcf 03h,5 			; Move back to 'Bank 0'.
	
	
	;---------------------------------------------------------------------------------------------------
start
	movlw b'00001'		; means 2 in decimal, 00010 in decimal. logic 1 to 2nd bit.
	movwf 05h 			; move logic 1 to 2nd Bit of PORTA. It let to on LED connected to 2nd bit i.s A1.
	
	call Delay 			;Call delay function
;	call Delay_0
	movlw 00h 			; to send 0 at w.
	movwf 05h 			; to get off lED.
	
	call Delay
;	call Delay_0 		; call delay function.

	GOTO start          ; COMPLETE LOOP


	;---------------------------------------------------------------------------------------------------

; SUBROUTINE CALLED DELAY
	

	;4999993 cycles
Delay movlw 0x2C
	movwf d1
	movlw 0xE7
	movwf d2
	movlw 0x0B
	movwf d3
Delay_0
	decfsz d1, f
	goto $+2
	decfsz d2, f
	goto $+2
	decfsz d3, f
	goto Delay_0
	
	;3 cycles
	goto $+1
	nop
	
	;4 cycles (including call)
	return
	;---------------------------------------------------------------------------------------------------
	end
 

Attachments

  • ScreenShot001.jpg
    ScreenShot001.jpg
    74.6 KB · Views: 378

Hi Again,

Everyone has their own way of coding , using the system register labels/ names is much easier than using the hex addresses like 03 and 05 which will only lead to confusion.

Code:
	LIST P=16f84
	
	#INCLUDE"P16f84.INC"	; all the system EQUATES are in this file   
							; It is located in Mpasm open it and have a look 
							; its complicated but it will make sense one day



	cblock 0x0c				; user registers
	d1
	d2
	d3
	COUNT
	endc

	;---------------------------------------------------------------------------------------------------
	banksel TRISA		; Moving from 'Bank 0' to 'Bank 1'.
	movlw b'00000' 		; Move adress 00000 to 'w' register .
	movwf TRISA			; move value of W into TRISA. It designate all bit output
	
	banksel 0			; Move back to 'Bank 0'.
	
	
	;---------------------------------------------------------------------------------------------------
start
	movlw b'00000001'	; load W to turn on Porta, bit 0
	movwf PORTA			; Move value in W to POORTA to turn on led on RA0
	
	call Delay5SEC		;Call delay function

	movlw b'00000000'	; Load W to turn off Portabit 0
	movwf PORTA			; Move value in W to POORTA to turn off led on RA0

	
	call Delay5SEC		; call delay function.

	GOTO start          ; COMPLETE LOOP


	;---------------------------------------------------------------------------------------------------

; SUBROUTINE CALLED DELAY
	

	;4999993 cycles
Delay5SEC movlw 0x2C
	movwf d1
	movlw 0xE7
	movwf d2
	movlw 0x0B
	movwf d3
Delay_0
	decfsz d1, f
	goto $+2
	decfsz d2, f
	goto $+2
	decfsz d3, f
	goto Delay_0
	
	;3 cycles
	goto $+1
	nop
	
	;4 cycles (including call)
	return						;  SPECIFIES THE END OF A SUBROUTINE
	;---------------------------------------------------------------------------------------------------


	end 						; SPECIFIES THE END OF ALL YOUR CODE
 

Status
Not open for further replies.

Similar threads

Part and Inventory Search

Welcome to EDABoard.com

Sponsor

Back
Top