Serial and interrupt


Closed Thread
Results 1 to 21 of 21
  1. #1
    Join Date
    Feb 2009
    Posts
    12

    Default Serial and interrupt

    How do one use a interrupt with the SERIN function? Basically what I'm trying to accomplish is to have a blinking LED and an interrupt on porta.5 - where I retrive a byte and then continue with the main loop.

    Currently my code isn't working as expected. It seems that the interrupt doesn't resume the main program loop after SERIN.

    I'm compiling for pic12f629.

    btw, to be able to do multitasking (updating LEDS and receiving from serial port) do I need to use interrupts?

    Code:
    INCLUDE "modedefs.bas" 'For the Baud Rate modes
    
    char var byte
    
    ON INTERRUPT GOTO myint ' Interrupt handler is myint
    
    INTCON.3 = 1 'PORTA change interupt enabled
    INTCON.7 = 1 'Global interrupt enabled
    IOC.3 = 1
    
    led_on:
    high porta.0
    pause 500
    low porta.0
    pause 500
    goto led_on
    
    ' Interrupt handler 
    DISABLE ' Disable interrupts in handler
    myint: 
    SerIN PORTA.3, T9600, ["b"],char    ' Will be uesed later
    INTCON.0 = 0 'Clear GPIF
    RESUME ' Return to main program
    ENABLE ' Enable interrupts after handler
    
    End

  2. #2
    Join Date
    Sep 2004
    Location
    montreal, canada
    Posts
    6,898


    Did you find this post helpful? Yes | No

    Default

    You just don't want to use a Software bit banged solution with interrupt. Move on a PIC with Real Hardware USART and use USART inetrrupt.

    It might be doable with your PIC, but on slower baudrate, using ASM interrupt (maybe instant interrupt), and an home made serial routine. No way this might work 100% properly with ON INTERRUPT even more with internal OSC.

    You could still try something and reduce your delay, using short PAUSEUS loop might work better.

    Using DEBUGIN would also help.

    If you build yourself the Master you could send few garbarge data, then a Synch character, then your data. Says
    SEROUT2 ....[REP 0\32, "~", YourData]

    on the receiver side you just use WAIT("~") ... might work.....
    Last edited by mister_e; - 4th February 2009 at 22:19.
    Steve

    It's not a bug, it's a random feature.
    There's no problem, only learning opportunities.

  3. #3
    Join Date
    Feb 2009
    Posts
    12


    Did you find this post helpful? Yes | No

    Default

    The thing is that it's kinda to late to change the pic for my current project

    Well it seems that I will be coding my own serial routine after all...

    In what way is the debugIN function different except the syntax?

    Do you have some more info about instant interrupt? Something to get me started.

    Anyway thanks for the help

  4. #4
    Join Date
    Sep 2004
    Location
    montreal, canada
    Posts
    6,898


    Did you find this post helpful? Yes | No

    Default

    DEBUGIN works better on higher baudrate on Slower Speed OSC. Check your manual about that. Syntax is a bit different as well.

    Instant-Interrupt
    http://darreltaylor.com/DT_INTS-14/intro.html
    Steve

    It's not a bug, it's a random feature.
    There's no problem, only learning opportunities.

  5. #5
    Join Date
    Feb 2009
    Posts
    12


    Did you find this post helpful? Yes | No

    Default

    Before posting posting to this forum I tried "DT_INTS-14" but I got some compailing errors, any idea how to fix them?

    Code:
    wsave3 position request 416 beyond RAM_END 95
    wsave2 position request 288 beyond RAM_END 95
    wsave1 position request 160 beyond RAM_END 95
    Unable to fit variable RS2_Save

  6. #6
    Join Date
    Sep 2004
    Location
    montreal, canada
    Posts
    6,898


    Did you find this post helpful? Yes | No

    Default

    open DT_INTS-14.bas file, there you'll find
    Code:
    ' --- IF any of these three lines cause an error ?? ---------------------------- 
    '       Comment them out to fix the problem ----
    ' -- It depends on which Chip you are using, as to which variables are needed --
    wsave1      var byte    $A0     SYSTEM      ' location for W if in bank1
    wsave2      var byte    $120    SYSTEM      ' location for W if in bank2
    wsave3      var byte    $1A0    SYSTEM      ' location for W if in bank3
    So, just modify it as requested
    Code:
    ' --- IF any of these three lines cause an error ?? ---------------------------- 
    '       Comment them out to fix the problem ----
    ' -- It depends on which Chip you are using, as to which variables are needed --
    ;wsave1      var byte    $A0     SYSTEM      ' location for W if in bank1
    ;wsave2      var byte    $120    SYSTEM      ' location for W if in bank2
    ;wsave3      var byte    $1A0    SYSTEM      ' location for W if in bank3
    Steve

    It's not a bug, it's a random feature.
    There's no problem, only learning opportunities.

  7. #7
    Join Date
    Feb 2009
    Posts
    12


    Did you find this post helpful? Yes | No

    Default

    So I did and now there's only one error left...
    Code:
    Unable to fit variable RS2_Save

  8. #8
    Join Date
    Sep 2004
    Location
    montreal, canada
    Posts
    6,898


    Did you find this post helpful? Yes | No

    Default

    well, seems we hit one of the limitation of the low-end PIC. In this case, asm INT and home made serial routine would work. 12F683 would provide better range.


    Let's see what Darrel would suggest...
    Last edited by mister_e; - 4th February 2009 at 22:52.
    Steve

    It's not a bug, it's a random feature.
    There's no problem, only learning opportunities.

  9. #9
    Join Date
    Feb 2009
    Posts
    12


    Did you find this post helpful? Yes | No

    Default

    I suppose that the only way to write the serial routine is to code it in asm.

    Damn me for choosing this somewhat limited pic

  10. #10
    Join Date
    Aug 2006
    Location
    Look, behind you.
    Posts
    2,818


    Did you find this post helpful? Yes | No

    Default

    12f683 is 8 pin device and has twice the flash memory available.
    If you do not believe in MAGIC, Consider how currency has value simply by printing it, and is then traded for real assets.
    .
    Gold is the money of kings, silver is the money of gentlemen, barter is the money of peasants - but debt is the money of slaves
    .
    There simply is no "Happy Spam" If you do it you will disappear from this forum.

  11. #11
    Join Date
    Feb 2009
    Posts
    12


    Did you find this post helpful? Yes | No

    Default

    Quote Originally Posted by Joe S. View Post
    12f683 is 8 pin device and has twice the flash memory available.
    Thanks for the tip, but I have already bought the other one - as I said to late to change my mind. Anyway i've been doing some diggin and I'm going forward with the ASM serial routine part. There's only one little problem - the code I'm using gives me a "Symbol previously not defined" error. How do I setup variables so I can write to them inside the asm code and reuse them in picbasic?

  12. #12
    Join Date
    Aug 2006
    Location
    Look, behind you.
    Posts
    2,818


    Did you find this post helpful? Yes | No

    Default

    Quote Originally Posted by test153 View Post
    Thanks for the tip, but I have already bought the other one - as I said to late to change my mind. Anyway i've been doing some diggin and I'm going forward with the ASM serial routine part. There's only one little problem - the code I'm using gives me a "Symbol previously not defined" error. How do I setup variables so I can write to them inside the asm code and reuse them in picbasic?
    I can answer that, I think. The name of your variable used in the asm routine needs to have an underscore preceding it in pbp, example:
    _MyVar var byte
    If you do not believe in MAGIC, Consider how currency has value simply by printing it, and is then traded for real assets.
    .
    Gold is the money of kings, silver is the money of gentlemen, barter is the money of peasants - but debt is the money of slaves
    .
    There simply is no "Happy Spam" If you do it you will disappear from this forum.

  13. #13
    Join Date
    Feb 2009
    Posts
    12


    Did you find this post helpful? Yes | No

    Default

    Quote Originally Posted by Joe S. View Post
    I can answer that, I think. The name of your variable used in the asm routine needs to have an underscore preceding it in pbp, example:
    _MyVar var byte
    Thanks, it worked. Now there only one other problem. I get a bunch of warnings about "Found opcode in column 1" and then MPASM gives me a "too many errors" message.

    Edit: Nevermind about that error, it turned out that one need a tab space before the asm commands.
    Last edited by test153; - 5th February 2009 at 23:59.

  14. #14
    Join Date
    Feb 2009
    Posts
    12


    Did you find this post helpful? Yes | No

    Default

    For the past few days I have been searching the net for some sample code for the soft uart - since I couldn't find anything useful that worked I ask you guys. Anyone that can point me to some site with anything useful?

    Also I found this asm code:
    Code:
    SERBUF var byte 
    TEMP var byte
    COUNTS var byte
    ASM
    ; ********************************************************************
    ; INCH ROUTINE
    ; THIS ROUTINE INPUTS RS232 DATA USING A 22K OHM RESISTOR, NO LEVEL-
    ; CHANGING INVERTER IS USED. GPIO,3 = RX (MARK = 0, SPACE = 1).
    ; THIS ROUTINE USES A 8-DATA BIT PER CHARACTER PROTOCOL.
    ; TO RECIEVE A CHARACTER, CALL inch. THE RECEIVED CHARACTER IS PLACED
    ; IN THE REG 'W' AND IN THE REG 'SERBUF'.
    ; CHARACTER WILL ECHO IF 'retlw 0' IS REM-ED OUT.
    ; VARIABLES USED: REG 'TEMP' AND REG 'SERBUF' BOTH VARIABLES ARE
    ; SHARED WITH THE 'outch' ROUTINE
    ; ROUTINES CALLED: 'half_baud' AND 'baud' FOR THE BAUD-RATE TIMING.
    ; ********************************************************************
    inch
        btfss GPIO,3 ; SKIP ON START BIT = "SPACE" (+RS232)
        goto inch ; ELSE KEEP LOOKING FOR A START BIT
        movlw d'08' ; START SERIAL INPUT SEQUENCE
        movwf _TEMP ; COLLECT 8 DATA BITS
        clrf _SERBUF ; CLEAR SERIAL CHARACTER BUFFER
        call half_baud ; DELAY FOR ONE HALF BAUD TIME
        btfss GPIO,3 ; FALL THRU IF START BIT STILL = "SPACE"
        goto inch ; ELSE IT WAS JUST A NOISE SPIKE, LOOP
    inch1
        call baud ; DELAY ONE BAUD-BIT TIME ( = 1/BAUD-RATE)
        bcf STATUS,0 ; CLEAR THE CARRY BIT
        rrf _SERBUF,F ; ROTATE CRY -> MSB, ROTATE MSB RIGHT
        btfss GPIO,3 ; IS INPUT = "SPACE" (+RS232) ?
        bsf _SERBUF,7 ; ...SKIP IF YES, ELSE SET BIT TO LOGIC '1'
        decfsz _TEMP,F ; EIGHT COUNTS YET?
        goto inch1 ; ...NO, GET ANOTHER BIT
        call baud ; DELAY FOR THE FIRST STOP BIT
        movf _SERBUF,W ; Put the character in reg 'W'
        retlw 0 ; NOTE: REM THIS OUT IF YOU NEED AN "ECHO"
        ; ...AND FALL THROUGH TO THE 'OUTCH' ROUTINE
        
    ; ********************************************************************
    ; BAUD ROUTINE @ 4 MHz
    ; BAUD RATE: CONSTANT:
    ; 1200 Baud D'137'
    ; 2400 Baud D'68'
    ; 4800 Baud D'34'
    ; 9600 Baud D'16'
    ; 19200 Baud D'8'
    ; 38400 Baud and up - use 'NOP' delays
    ; VARIABLES USED: REG 'COUNT'
    ; ROUTINES CALLED: NONE
    ; ********************************************************************
    baud            ; AT 2400 BAUD THE PERIOD IS 416.6 US
                    ; CLK = 4MHz
        movlw D'68' ; 1 US (BAUD RATE CONSTANT)
        movwf _COUNTS ; 1 US
    baud1
        decfsz _COUNTS,F ; 1 US (+ 1 US MORE IF SKIP)
        goto baud1 ; 2 US
        ; FALL THRU...AFTER 1+1+3x68+1 = 207 US
    half_baud
        movlw D'68' ; 1 US
        movwf _COUNTS ; 1 US
    hbaud1
        decfsz _COUNTS,F ; 1 US (+ 1 US MORE IF SKIP)
        goto hbaud1 ; 2 US
        retlw 0 ; ...AFTER 1+1+3x68+1 = 207 US (X2=414 US)
    ENDASM
    END
    I've tried it but I just get a "Stack underflow executing retlw". Also how do one call the inch routine from picbasic?
    Last edited by test153; - 7th February 2009 at 13:58.

  15. #15
    Join Date
    Sep 2004
    Location
    montreal, canada
    Posts
    6,898


    Did you find this post helpful? Yes | No

    Default

    RETLW 0 is the same (almost) as RETURN, this ca be remove if you're not using a GOSUB to call it. A return without a previous Gosub call, will indeed "underflow" the stack.

    If you sit this routine in a interrupt service routine, check the PBP manual somewhere at the end about INterrupts.
    Steve

    It's not a bug, it's a random feature.
    There's no problem, only learning opportunities.

  16. #16
    Join Date
    Feb 2009
    Posts
    12


    Did you find this post helpful? Yes | No

    Default

    Ok, so I need the interrupt to gosub the rs232 routine and how do I call a asm routine outside the asm...endasm?

  17. #17
    Join Date
    Aug 2006
    Location
    Look, behind you.
    Posts
    2,818


    Did you find this post helpful? Yes | No

    Default

    Quote Originally Posted by test153 View Post
    Ok, so I need the interrupt to gosub the rs232 routine and how do I call a asm routine outside the asm...endasm?
    Sec. 5.1 pbp: " When used at the beginning of a line, @ provides a shortcut for inserting one assembly language Statement into your PBP program."
    If you do not believe in MAGIC, Consider how currency has value simply by printing it, and is then traded for real assets.
    .
    Gold is the money of kings, silver is the money of gentlemen, barter is the money of peasants - but debt is the money of slaves
    .
    There simply is no "Happy Spam" If you do it you will disappear from this forum.

  18. #18
    Join Date
    Feb 2009
    Posts
    12


    Did you find this post helpful? Yes | No

    Default

    Well I have this code and still get underflow errors... I have a pritty good idea of what the code does, but I can't understand why it gives me this undeflow error as it is called from the main loop.
    Code:
    SERBUF var byte 
    TEMP var byte
    COUNTS var byte
    
    ASM
    ; ********************************************************************
    ; INCH ROUTINE
    ; THIS ROUTINE INPUTS RS232 DATA USING A 22K OHM RESISTOR, NO LEVEL-
    ; CHANGING INVERTER IS USED. GPIO,3 = RX (MARK = 0, SPACE = 1).
    ; THIS ROUTINE USES A 8-DATA BIT PER CHARACTER PROTOCOL.
    ; TO RECIEVE A CHARACTER, CALL inch. THE RECEIVED CHARACTER IS PLACED
    ; IN THE REG 'W' AND IN THE REG 'SERBUF'.
    ; CHARACTER WILL ECHO IF 'retlw 0' IS REM-ED OUT.
    ; VARIABLES USED: REG 'TEMP' AND REG 'SERBUF' BOTH VARIABLES ARE
    ; SHARED WITH THE 'outch' ROUTINE
    ; ROUTINES CALLED: 'half_baud' AND 'baud' FOR THE BAUD-RATE TIMING.
    ; ********************************************************************
    inch:
        btfss GPIO,3 ; SKIP ON START BIT = "SPACE" (+RS232)
        goto inch ; ELSE KEEP LOOKING FOR A START BIT
        movlw d'08' ; START SERIAL INPUT SEQUENCE
        movwf _TEMP ; COLLECT 8 DATA BITS
        clrf _SERBUF ; CLEAR SERIAL CHARACTER BUFFER
        call half_baud ; DELAY FOR ONE HALF BAUD TIME
        btfss GPIO,3 ; FALL THRU IF START BIT STILL = "SPACE"
        goto inch ; ELSE IT WAS JUST A NOISE SPIKE, LOOP
    inch1:
        call baud ; DELAY ONE BAUD-BIT TIME ( = 1/BAUD-RATE)
        bcf STATUS,0 ; CLEAR THE CARRY BIT
        rrf _SERBUF,F ; ROTATE CRY -> MSB, ROTATE MSB RIGHT
        btfss GPIO,3 ; IS INPUT = "SPACE" (+RS232) ?
        bsf _SERBUF,7 ; ...SKIP IF YES, ELSE SET BIT TO LOGIC '1'
        decfsz _TEMP,F ; EIGHT COUNTS YET?
        goto inch1 ; ...NO, GET ANOTHER BIT
        call baud ; DELAY FOR THE FIRST STOP BIT
        movf _SERBUF,W ; Put the character in reg 'W'
        retlw 0 ; NOTE: REM THIS OUT IF YOU NEED AN "ECHO"
        ; ...AND FALL THROUGH TO THE 'OUTCH' ROUTINE
        
    ; ********************************************************************
    ; BAUD ROUTINE @ 4 MHz
    ; BAUD RATE: CONSTANT:
    ; 1200 Baud D'137'
    ; 2400 Baud D'68'
    ; 4800 Baud D'34'
    ; 9600 Baud D'16'
    ; 19200 Baud D'8'
    ; 38400 Baud and up - use 'NOP' delays
    ; VARIABLES USED: REG 'COUNT'
    ; ROUTINES CALLED: NONE
    ; ********************************************************************
    baud:            ; AT 2400 BAUD THE PERIOD IS 416.6 US
                    ; CLK = 4MHz
        movlw D'68' ; 1 US (BAUD RATE CONSTANT)
        movwf _COUNTS ; 1 US
    baud1:
        decfsz _COUNTS,F ; 1 US (+ 1 US MORE IF SKIP)
        goto baud1 ; 2 US
        ; FALL THRU...AFTER 1+1+3x68+1 = 207 US
    half_baud:
        movlw D'68' ; 1 US
        movwf _COUNTS ; 1 US
    hbaud1:
        decfsz _COUNTS,F ; 1 US (+ 1 US MORE IF SKIP)
        goto hbaud1 ; 2 US
        retlw 0 ; ...AFTER 1+1+3x68+1 = 207 US (X2=414 US)
    ENDASM
    
    high porta.0
    loop:
    @   goto inch
    if SERBUF = 49 then low porta.0
    goto loop
    END

  19. #19
    Join Date
    Jul 2003
    Location
    Colorado Springs
    Posts
    4,959


    Did you find this post helpful? Yes | No

    Default

    Code:
    @   goto inch
    Try ...

    Code:
    @   L?CALL  inch
    DT

  20. #20
    Join Date
    Feb 2009
    Posts
    12


    Did you find this post helpful? Yes | No

    Default

    Some how I changed the line "@ call inch" to goto before posting. Using "@ L?CALL inch" didn't do anything...

  21. #21
    Join Date
    Jul 2003
    Location
    Colorado Springs
    Posts
    4,959


    Did you find this post helpful? Yes | No

    Default

    If that's your whole program, then you need to add a
    Code:
    GOTO  loop
    before the ASM block.

    As it's shown, it will fall into the inch routine on power-up.
    Then it has nowhere to return to.

    hth,
    DT

Similar Threads

  1. Instant Interrupts - Revisited
    By Darrel Taylor in forum Code Examples
    Replies: 772
    Last Post: - 17th February 2016, 22:14
  2. 18F2480 asm interrupt
    By Richard Storie in forum mel PIC BASIC Pro
    Replies: 3
    Last Post: - 5th March 2009, 19:40
  3. Serial and Port B interrupt
    By Pic2008 in forum mel PIC BASIC Pro
    Replies: 1
    Last Post: - 6th November 2008, 16:22
  4. timer and serial interrupt
    By yourmomOS in forum mel PIC BASIC Pro
    Replies: 3
    Last Post: - 14th July 2006, 18:02
  5. USART interrupt not interrupting right
    By Morpheus in forum mel PIC BASIC Pro
    Replies: 12
    Last Post: - 6th March 2005, 01:07

Members who have read this thread : 1

You do not have permission to view the list of names.

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts