Delay problems with assembly code and pic

Discussion in 'Embedded Systems and Microcontrollers' started by hunterage2000, Apr 12, 2014.

  1. hunterage2000

    Thread Starter Active Member

    May 2, 2010
    400
    0
    I have tried to create a delay to blink an led on and off using the below code but the led remains on. Can anyone see the prob.

    Code ( (Unknown Language)):
    1.  
    2. #include "p16F690.inc"
    3.  
    4.  __CONFIG H'30F0'
    5.  
    6. TMR0 equ 01
    7. STATUS equ 03
    8. PORTB equ 06
    9. TRISB equ 86
    10.  
    11. RES_VECT  CODE    0x0000            
    12.                  
    13. GOTO START
    14.  
    15. MAIN_PROG CODE
    16.                  
    17. ;DELAY
    18. DELAY1 CLRF TMR0 ;START TMR0.
    19. LOOPA MOVF TMR0,W ;READ TMR0 INTO W.
    20. SUBLW D'32' ;TIME - 32
    21. BTFSS STATUS,2 ; Check TIME-W¼0
    22. GOTO LOOPA ;Time is not¼32.
    23. RETLW 0 ;Time is 32, return.
    24.  
    25. START
    26. BCF STATUS,RP0 ;Bank 0
    27. BCF STATUS,RP1 ;
    28. CLRF PORTB ;Init PORTB
    29. BSF STATUS,RP0 ;Bank 1
    30. MOVLW 0x00
    31. MOVWF TRISB ;
    32. BCF STATUS,RP0 ;Bank 0
    33. LOOP BSF PORTB,6
    34.     CALL DELAY1
    35. BCF PORTB,6
    36. CALL DELAY1
    37.     GOTO LOOP                          ; loop forever
    38.  
    39.     END
    40.  
     
  2. ericgibbs

    AAC Fanatic!

    Jan 29, 2010
    2,503
    380
    hi 2000,
    What is the 16F690 Oscillator frequency to and what clock source are you using for TMR0.?

    E
     
  3. hunterage2000

    Thread Starter Active Member

    May 2, 2010
    400
    0
    I have used a 555 timer at 25Hz (EC) and a 32kHz small oscillator (LP). I have usee a 20MHz Epson crystal osc (XT) but not sure if I set it properly. Its pins is (1) OE, (2) GND, (3) OUT and (4) Vcc with OUT going to CLKIN. I wasn't sure about the decimal time used, I have seen D'32' and .32.
     
  4. JohnInTX

    Moderator

    Jun 26, 2012
    2,347
    1,029
    You have several problems here.

    First, you have to determine the flash rate and then how many Tcyc (Tosc/4) that is then determine how many TMR0 counts you have to accumulate. You haven't specified a prescaler using the OPTION register so its running so fast that you may not be able to see your LED blink at all.

    As an example at 4MHz Tcyc is 1uS. To blink the LED at 50ms on/off you need to count to 50,000 (50ms/1us). Using a prescaler of 256 with the internal clock source (OPTION= xx0x0111) you need to count 195.3 counts in the timer. So set OPTION and reload the timer to .256-.195 as shown in the code below. .256-.195=.61 i.e. set the counter to 61 and it will count up from there 195counts * 256prescaler * 1usTcyc ~= 50ms

    You are currently testing for zero (STATUS,2) i.e. testing for a timer value of exactly 32. That will be difficult to catch exactly when the timer is running very fast. A better way would be to count up from a value that is a number of counts from overflow then monitor TOIF.:
    Code ( (Unknown Language)):
    1.  
    2.  movlw .256-.195 ; init the timer
    3.  movwf TMR0
    4.  bcf INTCON,T0IF ; clear the overflow flag
    5. loop:
    6.  btfss INTCON,T0IF
    7.  goto loop
    8.  return
    9.  
    That way you can miss a couple of counts and still catch the overflow.

    This is not a particularly good way to get timer generated delays but its a start.

    Finally, you shouldn't define the PORTs, TRIS etc. That is done for you in the header file. As for _CONFIG, you should use the method called out in the header file and MPASM's help file. Using a hard-coded value is very error prone and virtually impossible to read.

    For value settings, I use . for decimal i.e. .10 and h for hex i.e. 0ah. MPASM accepts different ways as you have seen. The rule is be consistent and always specify the radix (hex, decimal, binary) explicitly for clarity and to guard against different defaults in various assembler configurations.

    Lastly, try to use STATUS,Z instead of STATUS,2 . That's easier to read. Even better is to use the built in macros i.e.
    skpz ; skip if STATUS,Z is set (zero result). Others are skpnz, skpc (skip on carry set), skpnc etc.

    Good luck.

    EDIT:
    Here's a starting point with some cleanups. You'll still need to determine the oscillator type/freq etc.
    Code ( (Unknown Language)):
    1. #include "p16F690.inc"
    2.  
    3.  ;__CONFIG H'30F0'
    4.  __CONFIG _LP_OSC & _WDT_OFF & _PWRTE_OFF & _MCLRE_ON & _CP_OFF & _CPD_OFF & _BOR_OFF & _IESO_OFF &_FCMEN_OFF
    5.  
    6. RES_VECT  CODE    0x0000            
    7.                  
    8.         GOTO    START
    9.  
    10. MAIN_PROG CODE
    11.                  
    12. ;DELAY
    13. DELAY1:
    14.         movlw    .256-.195  ; 50ms on, 50ms off at 4MHz
    15.         movwf    TMR0
    16.         bcf        INTCON,T0IF
    17. LOOPA:    
    18.         btfss    INTCON,T0IF
    19.         GOTO    LOOPA
    20.         RETLW 0
    21.  
    22. START:
    23.         ;BCF STATUS,RP0     ;Bank 0
    24.         ;BCF STATUS,RP1
    25.         banksel PORTB
    26.         CLRF PORTB            ;Init PORTB
    27.        
    28.         ;BSF STATUS,RP0     ;Bank 1
    29.         banksel TRISB
    30.         MOVLW 0x00
    31.         MOVWF TRISB ;
    32.         movlw    B'10000111'    ; RBPU off, PS=256, internal source
    33.         movwf    OPTION_REG
    34.  
    35.         ;BCF STATUS,RP0     ;Bank 0
    36.         banksel    PORTB
    37.  
    38. LOOP:
    39.         BSF PORTB,6
    40.         CALL DELAY1
    41.         BCF PORTB,6
    42.         CALL DELAY1
    43.         GOTO LOOP                          ; loop forever
    44.  
    45.     END
     
    Last edited: Apr 12, 2014
    ericgibbs likes this.
  5. MaxHeadRoom

    Expert

    Jul 18, 2013
    10,553
    2,375
  6. hunterage2000

    Thread Starter Active Member

    May 2, 2010
    400
    0
    Nice one guys, the delay is working. I will be going through Nigel's tutorials soon I reckon.
     
  7. atferrari

    AAC Fanatic!

    Jan 6, 2004
    2,648
    764

    You will learn a LOT there!
     
Loading...