Shop OBEX P1 Docs P2 Docs Learn Events
USB Datalogger help — Parallax Forums

USB Datalogger help

Danny O.Danny O. Posts: 6
edited 2008-08-08 18:16 in BASIC Stamp
Hi,

I am trying to learn to use the USB Datalogger (Vinculum) and need help with a couple i/o issues. DataloggerDemov1.0.bs2 and DataloggerTestV1.1.bs2 both run fine on my BS2.

I know so far that sending SEROUT TX\CTS, Baud, [noparse][[/noparse]"FWV", CR] will cause the Datalogger to return the FTDI firmware version (using this data merely as a test). I can't figure out how to actually get the data back to display in debug or on an LCD. I've used SERIN in attempts to get the data but after numerous failed iterations I'm left with no code and back at square one.

Once I have a grasp on the fundamentals of "talking" to the Datalogger, I'm confident I'll be able to do with it what I want. However, I'll soon need to figure out how to properly receive approx. 8k serially, write it to the Datalogger, and vice-versa. Yikes! (any advice in-advance?)

I would really appreciate any help I can get.


Many thanks.

Daniel Osterday

Comments

  • Danny O.Danny O. Posts: 6
    edited 2008-08-07 18:34
    Just to ensure I'm providing enough information to get adequate help, a portion of my troubled code is pasted below.

    Thanks again. Dan.


    ' {$STAMP BS2}
    ' {$PBASIC 2.5}

    '
    [noparse][[/noparse] I/O Definitions ]

    ' free are 8,9,10,11,12,13,14

    LCDpin PIN 15 ' LCD output

    USB_TX PIN 4 ' USB Transmit Data --> 27937.4 (RXD)
    USB_RTS PIN 5 ' USB Request To Send --> 27937.6 (CTS)
    USB_RX PIN 6 ' USB Receive Data <-- 27937.5 (TXD)
    USB_CTS PIN 7 ' USB Clear To Send <-- 27937.2 (RTS)


    '
    [noparse][[/noparse] Constants ]

    Baud2400 CON 396 ' 2400 baud
    Baud9600 CON 84 ' 9600 baud
    Baud19200 CON 32 ' 19200 baud

    cursHome CON 1 ' common commands
    clrLCD CON 12
    rArr CON 126
    lArr CON 127


    '
    [noparse][[/noparse] Variables ]

    bPort VAR INA ' buttons port
    btns VAR BYTE ' debounced inputs
    btns_state VAR BYTE ' button input state
    idx VAR BYTE ' loop counter

    timeout VAR BIT ' USB timeout indicator
    buffer VAR BYTE(15) ' USB input buffer
    index VAR BYTE ' USB index variable
    ioByte VAR BYTE ' USB i/o storage


    '
    [noparse][[/noparse] LCD Initialization ]

    LCD_Init:
    HIGH LCDpin ' initialize LCD transmit line
    PAUSE 100 ' pause for serial LCD to initialize
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$16,$0C,$11] ' LCD cursor off, clear display, lamp on
    PAUSE 5


    '
    [noparse][[/noparse] Main Code ]
    GOSUB USB_Init

    PAUSE 100
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$0C] ' clear the LCD
    PAUSE 5 ' 5ms pause after clearing LCD

    ' ***** MY TROUBLE SPOT START *****

    GOSUB Purge_USB_Buffer
    SEROUT USB_TX\USB_CTS, Baud9600, [noparse][[/noparse]"FWV", CR] ' transmit "FWV CR"
    PAUSE 200
    GOSUB Get_USB_Data
    SERIN USB_RX\USB_RTS, Baud9600, 800, No_USB_Data, [noparse][[/noparse]buffer]
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]buffer]

    ' ***** MY TROUBLE SPOT END *****


    END


    '
    [noparse][[/noparse] USB Drive Subroutines ]

    USB_Init:
    PAUSE 3000
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$BC,"Initializing"]
    HIGH USB_TX
    LOW USB_RTS ' take vinculum out of reset
    PAUSE 5000
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$BC,"Synchronizing"]
    PAUSE 4000
    GOSUB Purge_USB_Buffer ' purge USB buffer
    index = 0
    DO WHILE (index < 1)
    PAUSE 500
    SEROUT USB_TX\USB_CTS, Baud9600, [noparse][[/noparse]"E", CR] ' transmit "E CR"
    GOSUB Get_USB_Data ' get returned data
    LOOP
    GOSUB Purge_USB_Buffer ' purge USB buffer
    PAUSE 500
    SEROUT USB_TX\USB_CTS, Baud9600, [noparse][[/noparse]"e", CR] ' transmit "e CR"
    GOSUB Get_USB_Data ' get returned data
    PAUSE 500
    GOSUB Purge_USB_Buffer ' purge USB buffer
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$BC,"Testing Memory"]
    PAUSE 500
    SEROUT USB_TX\USB_CTS, Baud9600, [noparse][[/noparse]CR] ' transmit CR
    GOSUB Get_USB_Data ' wait for D:\>
    IF (buffer(0) = "N") THEN
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$BC,"Memory Error "]
    STOP
    ELSE
    PAUSE 250
    ENDIF
    GOSUB Purge_USB_Buffer ' purge USB buffer
    RETURN

    Purge_USB_Buffer:
    timeout = 1 ' set USB timeout indicator flag
    DO WHILE (timeout > 0) ' while USB timeout has not occurred
    PAUSE 50
    SERIN USB_RX\USB_RTS, Baud9600, 500, No_USB_Data, [noparse][[/noparse]ioByte]
    LOOP
    RETURN

    Get_USB_Data:
    timeout = 1 ' set USB timeout indicator flag
    index = 0 ' initialize USB index
    DO WHILE (timeout > 0) ' while USB timeout has not occurred
    ioByte = 0 ' clear USB temporary storage
    SERIN USB_RX\USB_RTS, Baud9600, 100, No_USB_Data, [noparse][[/noparse]ioByte]
    buffer(index) = ioByte ' save byte received to array
    index = index + 1 ' increment index
    IF (index > 14) THEN ' check For overflow
    index = 14 ' prevent overflow
    ENDIF
    LOOP
    RETURN

    No_USB_Data:
    timeout = 0 ' clear USB timeout indicator flag
    RETURN
  • SRLMSRLM Posts: 5,045
    edited 2008-08-07 18:51
    The easiest thing to do is to study the VDAP Firmware PDF file until you go blind, then look at the demo code that parallax provides. Modify the code to fit you application, keeping the stuff for starting/preparing the datalogger, and the subroutines. Keep in mind that when you want to read or write data, you have to send several arguments, where the last one is the number of characters that is going to be read/sent. If you use a modified version of the BS2 (like the BS2e or BS2px), then you can isolate your datalogger code.

    Take a look at the code that I used for a project. It's in Completed Projects under the title Swiftsure BS2e Robot. You could tanspose that dirrectly to a BS2, minus the SCRAM and slot stuff.
  • Danny O.Danny O. Posts: 6
    edited 2008-08-07 19:11
    I've read through the Firmware PDF, but nothing useful to me in there yet since, at this time, all I want to do is demonstrate the i/o by retrieving the FTDI firmware version and displaying it on an LCD.

    Thanks for the invite to your robot code but - unless I missed something - I didn't see any useful SERIN stuff in there.

    Do you/anyone else have any further advice?

    Dan
  • SRLMSRLM Posts: 5,045
    edited 2008-08-07 21:11
    Sorry. I confused that code with the code for my second version of the bot. I've went ahead and attached the new code. It has a section to read GPS coordinate data and place it into the SCRAM. Note that sometimes in the read, if I wanted it to ignore the formating I used a variable just to take up the space. These are easily differentiated by the lack of the DEC.
    ReadData:
      ' Open waypoints.TXT for input (read)
      PAUSE 200
      GET 54, destination
      SEROUT TX\CTS, Baud, [noparse][[/noparse]"OPR Waypoints.txt", CR]
      GOSUB Get_Serial_Bytes
      'To get the number of waypoints
      SEROUT TX\CTS, Baud, [noparse][[/noparse]"RDF ", $00, $00, $00, 3, CR]
      SERIN RX\RTS, Baud, 800, No_Data2, [noparse][[/noparse]DEC largeA.HIGHBYTE]
      PUT 55, largeA.HIGHBYTE
      'Want to run the loop (destination + 1) # of times
    
      'The loop is to get to the correct Destination Waypoint. Effectively reads and discards the previous ones.
      FOR counter = 0 TO destination
        PAUSE 200
        SEROUT TX\CTS, Baud, [noparse][[/noparse]"RDF ", $00, $00, $00, 12, CR]
        SERIN RX\RTS, Baud, 800, No_Data2, [noparse][[/noparse]largeA.HIGHBYTE, DEC largeA.HIGHBYTE, largeA.LOWBYTE, DEC largeA.LOWBYTE, largeB, DEC largeB]
        PUT 44, largeA.HIGHBYTE, largeA.LOWBYTE, Word largeB
        PAUSE 200
        SEROUT TX\CTS, Baud, [noparse][[/noparse]"RDF ", $00, $00, $00, 15, CR]
        SERIN RX\RTS, Baud, 800, No_Data2, [noparse][[/noparse]largeA.HIGHBYTE, DEC largeA.HIGHBYTE, largeA.LOWBYTE, DEC largeA.LOWBYTE, largeB, DEC largeB, largeC, DEC largeC]
        PUT 48, largeA.HIGHBYTE, largeA.LOWBYTE, Word largeB, Word largeC
      NEXT
      ' Close File
      PAUSE 120
      SEROUT TX\CTS, Baud, [noparse][[/noparse]"CLF Waypoints.txt", CR]
      GOSUB Get_Serial_Bytes
    

    The first SERIN Command is for a three digit number, the next SERIN expects 12, and so on. I found this to be very important. Keep·in mind that it helps if you know the format of your input file. I suppose that it's possible to interpret it real time with the BS2, but if you have a reasonable format all set out you can eliminate that.
  • Danny O.Danny O. Posts: 6
    edited 2008-08-08 16:41
    Thanks for the advice. My initial question has more-or-less been solved. The attached file is also pasted below with some heavily commented code excerpted from my project. My questions/concerns are pretty clear and I'd absolutely appreciate input from anyone.

    Dan


    ' {$STAMP BS2}
    ' {$PBASIC 2.5}

    '
    [noparse][[/noparse] I/O Definitions ]

    ' free are 8,9,10,11,12,13,14

    ' *** prefer using pin 0 as LCD instead. see var INA commenting below.
    LCDpin PIN 15 ' LCD output
    ' ***

    USB_TX PIN 4 ' USB Transmit Data --> 27937.4 (RXD)
    USB_RTS PIN 5 ' USB Request To Send --> 27937.6 (CTS)
    USB_RX PIN 6 ' USB Receive Data <-- 27937.5 (TXD)
    USB_CTS PIN 7 ' USB Clear To Send <-- 27937.2 (RTS)


    '
    [noparse][[/noparse] Constants ]

    Baud2400 CON 396 ' 2400 baud
    Baud9600 CON 84 ' 9600 baud
    Baud19200 CON 32 ' 19200 baud

    cursHome CON 1 ' common commands
    clrLCD CON 12
    rArr CON 126
    lArr CON 127


    '
    [noparse][[/noparse] Variables ]

    ' *** INA defined here but pins 1,2,3 are the only one used. how to redefine pin 0 as
    ' the serial LCD pin instead of pin 15?
    bPort VAR INA ' buttons port
    ' ***

    btns VAR BYTE ' debounced inputs
    btns_state VAR BYTE ' button input state
    idx VAR BYTE ' loop counter

    timeout VAR BIT ' USB timeout indicator
    buffer VAR BYTE(15) ' USB input buffer
    index VAR BYTE ' USB index variable
    ioByte VAR BYTE ' USB i/o storage
    ' ***


    ' *** how inefficient is this? the only reason for var ftdi is for proper re-display
    ' *** on LCD. prefer utilizing SERIN more effectively to not need var ftdi.
    devinfo VAR WORD ' versions etc.
    ftdi VAR devinfo.BYTE1
    ' ***


    '
    [noparse][[/noparse] LCD Initialization ]

    LCD_Init:
    HIGH LCDpin ' initialize LCD transmit line
    PAUSE 100 ' pause for serial LCD to initialize
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$16,$0C,$11] ' LCD cursor off, clear display, lamp on
    PAUSE 5


    '
    [noparse][[/noparse] Main Code ]
    Splash:
    GOSUB USB_Init
    GOTO Main_Menu1


    Main_Menu1:
    PAUSE 100
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$0C] ' clear the LCD
    PAUSE 5 ' required 5ms pause after clearing LCD
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$BE,lArr,$C5,rArr,$CC,"OK",$80] ' left, right, OK menu buttons. return home
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]CR,"main"]

    ' *** is this necessarily the best way to create a three-option menu?
    DO
    GOSUB GetBtn
    IF btns = %0001 THEN Device_Info
    IF btns = %0010 THEN Device_Info
    IF btns = %0100 THEN Device_Info
    LOOP
    ' ***

    Device_Info:
    PAUSE 100

    ' *** an error occurs here which prevents INA from working as buttons
    ' *** this code itself works, aside from the other problems it created
    SEROUT USB_TX\USB_CTS, Baud9600, [noparse][[/noparse]"FWV", CR]
    SERIN USB_RX\USB_RTS, Baud9600, 800, No_USB_Data2, [noparse][[/noparse]STR devinfo\16]
    ' ***

    GOSUB Purge_USB_Buffer
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$0C] ' clear the LCD
    PAUSE 5 ' required 5ms pause after clearing LCD
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$CC,"OK"] ' OK menu button

    ' *** start part 3 / this seems really inefficient to me but it works.
    ' *** see var ftdi commenting above
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$80,"DEO 01.00",$97,STR ftdi,$94,"FTDI"]
    ' ***

    DO
    GOSUB GetBtn
    IF btns = %0100 THEN Main_Menu1
    LOOP


    END


    '
    [noparse][[/noparse] Button Subroutines ]

    GetBtn:
    btns = %0111 ' enable all four inputs
    FOR idx = 0 TO 2
    btns = btns & ~bPort ' test inputs
    PAUSE 15 ' 15ms delay between tests
    NEXT
    RETURN


    '
    [noparse][[/noparse] USB Drive Subroutines ]

    USB_Init:
    PAUSE 3000
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$BC,"Initializing"]
    HIGH USB_TX
    LOW USB_RTS ' take vinculum out of reset
    PAUSE 5000
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$BC,"Synchronizing"]
    PAUSE 4000
    GOSUB Purge_USB_Buffer ' purge USB buffer
    index = 0
    DO WHILE (index < 1)
    PAUSE 500
    SEROUT USB_TX\USB_CTS, Baud9600, [noparse][[/noparse]"E", CR] ' transmit "E CR"
    GOSUB Get_USB_Data ' get returned data
    LOOP
    GOSUB Purge_USB_Buffer ' purge USB buffer
    PAUSE 500
    SEROUT USB_TX\USB_CTS, Baud9600, [noparse][[/noparse]"e", CR] ' transmit "e CR"
    GOSUB Get_USB_Data ' get returned data
    PAUSE 500
    GOSUB Purge_USB_Buffer ' purge USB buffer
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$BC,"Testing Memory"]
    PAUSE 500
    SEROUT USB_TX\USB_CTS, Baud9600, [noparse][[/noparse]CR] ' transmit CR
    GOSUB Get_USB_Data ' wait for D:\>
    IF (buffer(0) = "N") THEN
    SEROUT LCDpin, Baud19200, [noparse][[/noparse]$BC,"Memory Error "]
    STOP
    ELSE
    PAUSE 250
    ENDIF
    GOSUB Purge_USB_Buffer ' purge USB buffer
    RETURN

    Purge_USB_Buffer:
    timeout = 1 ' set USB timeout indicator flag
    DO WHILE (timeout > 0) ' while USB timeout has not occurred
    PAUSE 50
    SERIN USB_RX\USB_RTS, Baud9600, 500, No_USB_Data, [noparse][[/noparse]ioByte]
    LOOP
    RETURN

    Get_USB_Data:
    timeout = 1 ' set USB timeout indicator flag
    index = 0 ' initialize USB index
    DO WHILE (timeout > 0) ' while USB timeout has not occurred
    ioByte = 0 ' clear USB temporary storage
    SERIN USB_RX\USB_RTS, Baud9600, 100, No_USB_Data, [noparse][[/noparse]ioByte]
    buffer(index) = ioByte ' save byte received to array
    index = index + 1 ' increment index
    IF (index > 14) THEN ' check For overflow
    index = 14 ' prevent overflow
    ENDIF
    LOOP
    RETURN

    No_USB_Data:
    timeout = 0 ' clear USB timeout indicator flag
    RETURN

    No_USB_Data2:
    DEBUG CR, "Error reading the seed file -- Halting execution!", CR
    PAUSE 1000
    GOSUB Purge_USB_Buffer ' Purge Buffer
    STOP
    RETURN
  • UnsoundcodeUnsoundcode Posts: 1,532
    edited 2008-08-08 18:16
    Hi Daniel, with regard to the Lcd and button pinout there is nothing to prevent you using P0 as the Lcd pin. Your only concern would be to filter the bits you require from INA (1,2 &3), you have several options for a menu the following is an example

    btns VAR Nib
    DO WHILE btns=0
    btns=INA>>1 & 7· 'shift the 4 bits right 1 place and filter the relative 3 bits (P1 2 & 3)
    LOOP
    ON btns GOSUB no_task,task_1,task_2,task_3

    I scanned your listing real quickly I hope this along the right lines

    Jeff T.
Sign In or Register to comment.