Darrel Taylor Elapsed Timer


Closed Thread
Results 1 to 15 of 15

Hybrid View

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


    Did you find this post helpful? Yes | No

    Default

    It might be a little better, but there's a much better way.

    Receive 1 byte at a time in the handler

    If you get an interrupt from the USART, you are guaranteed that there is at least 1 byte in the USART's buffer.

    So when you get to the handler, just get the byte that you know is there. No Timeouts, no sitting around waiting for the next byte to finally come in. Serial data is Really slow compared to the speed of the processor. It doesn't make sense to waist millions of instructions sitting around waiting for serial data.

    After getting the byte, exit the Handler. If there is another byte still in the buffer, then DT_INT's will automatically loop back around to grab the next one, without ever leaving the interrupt processor.

    Then all you need to do is watch for the synchronizing character, and count how many bytes have been received. If you get a sync byte, reset the count. If you count the correct number of bytes received, set a flag to tell the main loop that the receive succeeded.

    Something like this off the top of my head...
    Code:
    TempByte  VAR BYTE
    RXdone    VAR BIT
    
    'Receive Interrupt 
    Receive: 
        HSERIN [TempByte]          ; Get the byte
        IF (TempByte = MyID) THEN  ; is it the sync byte?
            Cnt = 0                ; Yes, reset the counter
            RXdone = 0             ; indicate, RX not finished
            @  INT_RETURN          ; Return, and discard the sync byte
        ENDIF  
    
        BufRX(Cnt) = TempByte      ; Not a sync byte. save it.
        Cnt = Cnt + 1              ; increment buffer pointer
    
        IF (Cnt = 7) THEN          ; If all bytes are received?
            RXdone = 1             ; Tell Main loop to process it.
    
                                         ; If the main loop cannot process
    ;       FOR Cnt = 0 to 6             ; the data before the next sync byte?
    ;          RX_Data(Cnt) = BufRX(Cnt) ; Copy it to another "Working" buffer
    ;        NEXT Cnt                    ; Reception will continue while the 
        ENDIF                            ; last packet is processed
                                         
    @ INT_RETURN
    
    ;---------------------------------------
    Main:
    ;   ...
        IF RXdone then Gosub ProcessData
    ;   ....
    GOTO Main
    
    ;---------------------------------------
    ProcessData:
        RXdone = 0
    ;   ....
    ;   ....
    RETURN
    This will use the least amount of time required to receive serial data. And the main loop has much more time to do whatever it needs to. And allows many more interrupts to happen too, if needed.

    Just make sure that the Sync byte can NEVER be found in the data bytes. This goes for the way you had it too.

    If you are sending data in the form of Bytes, it's likely that a data byte will have the same value as the sync byte. If that's possible, you'll need to develop a multi-byte synchronization, or transmit the data in plain text (HEX is the easiest).

    HTH,
    <br>
    DT

  2. #2
    Join Date
    Oct 2005
    Posts
    74


    Did you find this post helpful? Yes | No

    Default

    Thanks for your help Darrel

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


    Did you find this post helpful? Yes | No

    Default

    That sounded like a ... "Thanks, but No Thanks".

    OK, but it is the Best way to receive serial from the USART.
    <br>
    DT

  4. #4
    Join Date
    Oct 2005
    Posts
    74


    Did you find this post helpful? Yes | No

    Default

    No, not at all, was just thanking you for the help you've given. Too many times I look the time to search and look up links and info for folks and not even a reply or thank you.

    I see it happen to folks here all the time. (like all the modbus questions a few days ago. not a thank you or reply one)

    The buffer is a fine idea, I usually do this in low level serial work as well on pc's. For your question, the sync byte is simply a single byte that is the ID of the system it's meant for. When you see it, you either collect 7 more bytes or timeout. After you collect the total of 8 bytes (including the ID) you then first check to see if the last two bytes calculates to the CRC of the message you received. If not, toss it. There are numerous other checks as well.

    So, No Start Byte besides the ID,
    No terminator, just a silent time to time out on. Usually collect 8 bytes for a valid message depending on mode.

    In total it goes something like this.

    1)Grab a byte, is it my ID? No, then ignore it. Yes then go to next step.
    2) Collect a total of 8 bytes or timeout and clear the buffer.
    3) e collected 8 bytes, now get the last two bytes and calc the 16 bit CRC and see if it matches the message. if so next, or ignore message.
    4) now check to see if the Function Code is valid or supported, if not, return an error message FC Invalid, else process the request.
    5) Return the required Data

    The thing is, since it's only 8 bytes of data, it doesn't really take that long and other than gathering a few adc readings there isn't much else going on, so I took the simple route.

    I still have to figure out how to use 7,N,1 with the usart by shifting bits for valid data or something. Hadn't played with it, took the software serial routines for that portion but I think with a little logic I could shift 1 bit before storing the 7 bit value in the array and do the same when sending it and making the last bit a 1 for a stop bit.

    Something to play with I guess.


    Richard

Similar Threads

  1. Elapsed Timer Demo
    By Darrel Taylor in forum Code Examples
    Replies: 111
    Last Post: - 29th October 2012, 17:39
  2. High Resolution Timer & Speed Calculator
    By WOZZY-2010 in forum Code Examples
    Replies: 4
    Last Post: - 7th February 2010, 16:45
  3. Timer interrupt frequency
    By Samoele in forum mel PIC BASIC Pro
    Replies: 1
    Last Post: - 17th January 2009, 23:49
  4. using darrel taylor's instant interrupts
    By Michael Wakileh in forum mel PIC BASIC Pro
    Replies: 13
    Last Post: - 31st July 2007, 04:07
  5. timer interupt help 16f73
    By EDWARD in forum mel PIC BASIC Pro
    Replies: 5
    Last Post: - 3rd July 2005, 08:41

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