This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

Reset RX and TX Buffers in USB_BULK

I am using CCS  Version: 6.1.0.00104  and a TM4C123XGL development board.  I am using the example USB_BULK.  It transfers great if you want to get the data you send back all day but not much use for that.

When data is received the read indexes continue to grow and the receive buffer keeps getting fuller.  How do you recieve the first data and then clear the recieve and transmit buffers as though you have never received any data.  I want to receive like 4 characters, process this data and send it back at a later time.  I have used USBBufferFlush(&g_sRxBuffer) and USBBufferFlush(&g_sTxBuffer);.  I read somewhere that they don't work in bulk, and they don't.

Any help would be appreciated.

  • Moving to the correct forum.
  • Hello Donald,

    Is the issue really to change the read index or clear the buffer?

    Regards
    Amit
  • The problem as I see it is the underlying USBBulk.c in the library. It's almost the same as the USB_bulk.c that is in the workspace. Every time I change some of the program in the receive section in the outer shell, it appears that the pointers get all messed up, which effects the transmit part of the event. I guess I,m looking for a USB transfer program that uses USBLIB without the two layers used in the USB_Bulk routine. I'm not that experienced a programmer to design such a program. I don't want to use the USBserial because I'm trying get away from serial. In some of the comments in the library they talk about block transfers instead of bulk transfers, but I can't find any examples to that effect. Any pointers in modifying the existing bulk transfer or USB examples would be appreciated.
    Administrative Question:
    I'm not getting any emails when I get a response even if I check the box, any suggestion
  • Hi Donald,
    The USB bulk client example can be launched switch (-e) and modified to TX launch pad data into the Windows USB bulk client. BTW this is high speed serial in device mode is said to top 1.5mbps. The bulk client reports a TP of 250kbps for simple USBprinf() data.

    e2e.ti.com/.../439435
  • I don't think you understand my problem. I want to get "4000" from the host, which I can do, add the character "V" to it and send it back. It will do it on the first try but on the second the RX buffer has "40004000". When I try to add the V and send it back. By adding the character V, pointers get messed up because the TX is expecting four characters not 5. What I want is to receive 4 characters , clear out the RX buffer and TX buffer, reset the pointers to lets say zero so the next data received is 4000 and V4000 is sent. I have tried clearing the buffer by using memset( g_pui8USBRxBuffer,'\0', sizeof(255) ). This works but the underlying layer doesn't like it. Seems everyone's got speed as the problem, it's not. Its a good example to show that is can send and receive data, but its not a very good example to try to modify because of the two layers of protocol. Serial is not USB. You have to set up baud rates, ports and protocols on both the host and the client, USB you plug and go.
  • Hello Donald,

    I think there are 2 sets of changes, considering your application code where the PC sends a string of N characters but can receive M characters from the uC later.

    1. The Code in the uC needs to be changed to handle TX and RX buffer differently
    2. The USB Application on the PC host needs to be changed to read and write independent of each other.

    Correct me if I have not understood the problem statement? I am working on a similar code but I decided to break out of usblib for a reason (the code will not be available till all documentation and approvals are in place). Moving it back to usblib can be done: just that we would need to collaborate.

    Regards
    Amit
  • Serial is not USB.  You have to set up baud rates, ports and protocols on both the host and the client, USB you plug and go.

    Actually USB is a serial data stream - don't get your point here. I didn't infer for you to use a serial virtual CDM driver or UARTprintf().

    Check again the call is USBprintf() which sends TM4C TX data direct to the modified windows client bulk USB example. Take what you can from the posted code snippets to make your custom program work.

    The USB host side bulk example FIFO are flushed with following code:        

    USBBufferFlush(&g_sTxBuffer);           

    USBBufferFlush(&g_sRxBuffer);

    Adding V to 4000 in the RXBuffer as you know requires to modifying the Rx callback character loop counter found in (EchoNewDataToHost). One problem you might be having is the RX call back directly writes RX characters into TX buffer prior to sending any data back to the device channel. USBprintf() writes data direct into the channel via (USBbufferWrite()) immediately sending the data on the USB channel to the connected end point. The double 4k4k is the Echo subroutine is not flushing the RX buffer after each TX buffer cycle, easily fixed adding above flush to the Echo routine.

     

  • My process on the host is set up to do either. If want I can send data with no intention of getting any data back. I can have it constantly listen for any interrupt and process that data separately. Its not looking for information just because I sent out something. It a simple routine written in Visual Studio C# and uses the LibUsbDotNet library. You have understood the problem very well. I think the whole USB community is looking for a simple routine that can send buffer data data without ever receiving any and receive data without ever intending to send data back.
  • The USBBufferFlush(&g_sTxBuffer); on my program doesn't flush anything. If I put it after USBBufferDataWritten(&g_sTxBuffer, ui32Count); and set a breakpoint the data is still there. If it works for you is there something special you are doing to get it to work?
  • I just found a possible work around, but boy is it ugly. I don't even want to suggest it as an answer. I want Amit to continue with his program, in fact I,m sure he probably needs someone to test his solution. I'mm 66 years old, hope he gets it completed before it's too late. What I found is if you re-initialize after the transfer the buffers and pointers are re-aligned. Haven't been able to test the solution extensively and I,m sure there will be repercussions from it. This is what I did!

    USBBufferDataWritten(&g_sTxBuffer, ui32Count);

    USBBufferInit((tUSBBuffer *)&g_sTxBuffer);

    USBBufferInit((tUSBBuffer *)&g_sRxBuffer);

    USBBufferFlush(&g_sTxBuffer);

    USBBufferFlush(&g_sRxBuffer);
  • >The USBBufferFlush(&g_sTxBuffer); 

    I was referring to flush the RXBuffer after each TXBuffer write so the RX data of the last cycle is not appended to the TX data of the present cycle. The unmodified TM4C bulk USB code was looping the terminals Echo output at high speed likely since it had a CR terminated at the end of the string. 

    The VS C++ bulk client example can be imported and easily modified into an RX dumb terminal and launched with the (-e) switch it will report the TP speed. When bulk client is configured in TX mode only the TM4c code side USB_bulk_buffer_size has to be increased to 2048 bytes testing the buffer has some space remaining prior to each USBbuffferWrite() cycle. USB serial TX is that fast, it will quickly fill the 2048 buffer.

    http://software-dl.ti.com/tiva-c/SW-TM4C/latest/index_FDS.html

        //
        // How much space is there in the transmit buffer?
        //
         ui32Space = USBBufferSpaceAvailable(&g_sTxBuffer);
    
        //
        // If the USB buffer space will not hold the
        // string try again later when it will.
        //
        if(ui32Space < 256)
        {
          /* Flush the TX buffer of any overflow data */
            USBBufferFlush(&g_sTxBuffer);
        	return;
        }

  • Hello Donald,

    That WA could hold. I am using the USB controller outside the usblib and it is a small 500 line code in C that allows me to exchange data w/o doing a complementary action.

    Regards
    Amit
  • Hi Don,

    The link in last post leads to DL Windows bulk USB client MSVS Visual Studio project. You mentioned writing a custom C# client - sounds interesting assume it uses .NET2.0 to help implement USB client access to the ACP compliant device driver layer? Good to know the TI end point USB device driver is not explicitly required. That USB bulk TI device driver sometimes disconnects the host from client console for no apparent reason.

    That said we currently can not use the TI bulk USB client with the (-e) switch enabled to send data back to the host LP as there is no split display or command entry window. Would have been helpful a more advanced TI programmer build that bulk USB multitasking console. Also the USB code (LP side) we now use to peak into the FIFO for a CR terminator is not yet written as it exists only for UARTs. That polling (peak) function scans the client command line entry received from the character string sent back to the host LP upon a user CR key stroke.

    This case bulk USB device LP side the RX event flag function call would make a great place to (peak) for that CR. Course the client part has to have a command line added. I haven't had time to see if the C+ CMD console being used can be invoked in split screen mode to add that ability. Something in gut tells me not possible, a bulk client rewrite using IE hooks is necessary to achieve that.