4 Replies Latest reply on Nov 16, 2017 2:28 PM by user_365962704

    USBFS DMA behaviour

    TelmoBarros

      I've read the datasheet of USBFS and noticed that it is possible to implement it with the DMA. My situation is that I have an array with 128 samples (2 bytes each) and I want to transfer these over to the PC (python program).

      The pyusb implementation limits the transfers to 64 bytes, so I use the Bulk transfer on the PSoC and, so far, I was able to transfer 64 bytes of data (actually 32 because it divides the 2 bytes samples).

      So, my question, regarding the DMA is: shouldn't it send the first 64 bytes and, right after queue the next samples to be sent, doing this process until it reaches the end of the sample array?

       

      Attached is my project called "PSoCandPYTHON"

        • 1. Re: USBFS DMA behaviour
          anks

          You can check into this project in which circular buffer -

          PSoC 4 Pioneer Kit Community Project#102 – USB ... | element14 | Cypress Kits

          Its an old project, it may not build in latest version of creator.

          You can make use of DMA with Manual Buffer Management option, but the here the transfers may be slow as all will be handled by CPU.

          • 2. Re: USBFS DMA behaviour
            user_365962704

            I couldn't get the USB component to send more than 64bytes on one packet (this limitation when using BULK) nor being able to the DMA Automatic handle to send the next 64 bytes on the second transaction.

             

            I modified your project to use Manual memory handing and now i can send the whole array to the pc, as the data you were trying to send is uint16_t and the USB can send uint8_t data i used a union:

            union Data {
                 uint16_t      u6_buffer[128], // your original buffer
                 uint8_t     u8_buffer[256], // "virtual" buffer
            };
            

             

            And Load the data to the IN endpoint like:

            union Data myData = {
                 .u16_buffer = { // content of the buffer 
                 }
            }
            
            USB_LoadEPIn(IN_EP, &myData.u8_buffer[0], 64);
            

             

            The python script:

            #!/usr/bin/env python3
            
            
            import time
            import usb.core
            import usb.util
            import numpy as np
            import sys
            
            def close_device(exitVal=0):
                print("Exiting...")
                usb.util.dispose_resources
                sys.exit(exitVal)
            
            ###########USBFS Configuration (Python side)###########
            VID = 0x04B4
            PID = 0xF232
            
            dev = usb.core.find(idVendor = VID, idProduct = PID)
            
            if not dev:
                print('PSoC not found')
                close_device(1)
            
            print('PSoC found')
            #set the active configuration (basically, start the device)
            dev.set_configuration()
            
            #get interface 0, alternate setting 0
            cfg = dev.get_active_configuration()
            intf = cfg[(0, 0)]
            
            epOut = usb.util.find_descriptor(
                intf,
                # match the first OUT endpoint
                custom_match= \
                lambda e: \
                    usb.util.endpoint_direction(e.bEndpointAddress) == \
                    usb.util.ENDPOINT_OUT)
            
            
            #make sure our endpoints were found
            if epOut is None:
                close_device(1)
            
            
            # find the first (and in this case only) IN endpoint in our interface
            epIn = usb.util.find_descriptor(
                intf,
                custom_match= \
                lambda e: \
                    usb.util.endpoint_direction(e.bEndpointAddress) == \
                    usb.util.ENDPOINT_IN)
            
            
            #make sure our endpoints were found
            if epIn is None:
               close_device(1)
            
            
            ###########USBFS Configuration (Python side)###########
            
            
            #print("Message: ")
            # obtenemos la entrada del usuario
            #t = input()
            # escribimos la entrada del usuario al OUT endpoint
            #dataWriten = epOut.write(t)
            
            
            # if using BULK transfers we are stuck at 64 bytes
            bytes_to_read = 64
            
            
            for i in range(10):
                time.sleep(0.25)
            
            
                # "trigger" the data transfer
                try:
                    print("Triggering the data transfer")
                    epOut.write('2')
                except usb.core.USBError:
                    print("Can't send data to the PSoC")
                    close_device()
            
            
                data = epIn.read(bytes_to_read)
            
            
                # print data in decimal
                # we get the data in u8 format so to transform it into u16
                # we need to shift the high_byte 8 positions to the left
                # and OR it with the lower_byte
                # Repeat it depending of the number of bytes to read
                for i in range(0, bytes_to_read, 2):
                    print('Received: {0:d}'.format(data[i+1] << 8 | data[i]))
            
            
            close_device()
            

             

            The project is attached.

            • 3. Re: USBFS DMA behaviour
              TelmoBarros

              Gracias por la ayuda!

              • 4. Re: USBFS DMA behaviour
                user_365962704

                Hope it helps to solve your project.

                1 of 1 people found this helpful