4 Replies Latest reply on May 28, 2019 3:26 AM by KandlaguntaR_36

    CX3 DMA issue




      We are working on a CX3 and we have a working set (sensor + HW + SW).

      Currently we are able to get 6fps (4096x3072 pixel/frame) and we want to increase this rate.


      We plan to:

      Increase USB data rate.

      Increase DMA buffers size to fit USB burst.

      and finally change CX3 MIPI receiver configuration and sensor configuration.

      Do we start from the right side ?


      we are working with an ISO EP and plan to increase burst length from 8 to 12.

      Iso packets is set to 3 and packet size to 1024. So from AN86947 we should achieve around 287.9MB/s (theorically: 3*12*1024*8000 B/s).


      We understand from datasheet/AN/documentation/community topics that the multichannel DMA connected to the EP should be of the same size as data sent per service interval.

      In our case, we are currently working with 24KB/ SI and we want to increase it to 36KB/ SI.

      So we need to increase our DMA buffer to 36KB.


      We are using the following DMA cfg:

      l_t_DmaCfg.size           = 24576;

      l_t_DmaCfg.count          = 4;

      l_t_DmaCfg.validSckCount  = 2;

      l_t_DmaCfg.prodSckId[0]   = CY_U3P_PIB_SOCKET_0;

      l_t_DmaCfg.prodSckId[1]   = CY_U3P_PIB_SOCKET_1;

      l_t_DmaCfg.consSckId[0]   = CY_U3P_UIB_SOCKET_CONS_3;

      l_t_DmaCfg.dmaMode        = CY_U3P_DMA_MODE_BYTE;

      l_t_DmaCfg.notification   = CY_U3P_DMA_CB_PROD_EVENT | CY_U3P_DMA_CB_CONS_EVENT;

      l_t_DmaCfg.cb             = sgm_cb_ManageStream;

      l_t_DmaCfg.prodHeader     = 192;

      l_t_DmaCfg.prodFooter     = 0;

      l_t_DmaCfg.consHeader     = 0;

      l_t_DmaCfg.prodAvailCount = 1;


      First issue:

      We are using default memory map, so 224KB are reserved for buffers.

      If we just change DMA size, we obviously have an error (36KB x 4 buffers x 2 sockets = 288KB) because we demand more space than available.

      CyU3PDmaMultiChannelCreate returns CY_U3P_ERROR_MEMORY_ERROR. (0x10)

      So we tried to reduce the DMA buffer number, from 4 to 2 (36KB x 2 buffers x 2 sockets = 144KB).

      CyU3PDmaMultiChannelCreate is working.

      But we have an error when, later, we call a reset (CyU3PDmaMultiChannelReset). the error code is 0x40 (CY_U3P_ERROR_BAD_ARGUMENT).

      We don't have it when we keep 4 buffers per socket.

      We don't understand why we get this error.

      Any idea ?


      Thank you.



        • 1. Re: CX3 DMA issue

          Hello Benjaman,


          >> Do we start from the right side ?

          You can start either way.


          You can get additional 32 KB buffer for DMA, if you do the following in fxtx.c file.


          DMA Buffer:


          If you are using UVC class, please update the probe control structure as per DMA buffer size.

          If you need to add EOF in DMA header, ensure that the frame size is not interger multiple of buffer size. Otherwise, you will not get the partial buffer.


          Increase the DMA memory size (244 + 32 KB): 


          The last 32 KB of RAM is reserved for 2-stage boot operation. This value can be

             changed to 0x40080000 if 2-stage boot is not used by the application.


          #define CY_U3P_SYS_MEM_TOP           (0x40078000)

          CyU3PDmaMultiChannelReset Fails:


          Please confirm whether you are passing the correct handle to CyU3PDmaMultiChannelReset API.

          Please print the multichannel start signature and end signature and check with the following values:



          CyU3PDebugPrint(4, "DMA CHannel = %x \r\n", (glChHandleBulkLp.startSig) );


          \brief Signature used to identify start of a valid DMA multi-channel structure.

          #define CY_U3P_DMA_MULTICHN_START_SIG           (0x4D4C4348)


          \brief Signature used to identify the end of a valid DMA channel or multi-channel structure.


          #define CY_U3P_DMA_CHANNEL_END_SIG              (0x454E4443)






          • 2. Re: CX3 DMA issue

            Hi KandlaguntaR_36,


            We are using a handle create with CyU3PDmaMultiChannelCreate.

            here is our function that initialize DMA:

            static CyU3PReturnStatus_t sgm_t_InitializeStreamTransfer(void)


                CyU3PDmaMultiChannelConfig_t l_t_DmaCfg;

                CyU3PReturnStatus_t          l_t_Status;


            #if ENABLE_MUTEX

                CyU3PMutexCreate (&sgm_mutex, CYU3P_NO_INHERIT);



            /* Create a DMA Manual OUT channel for streaming data                      */

            /* Video streaming Channel is not active till a stream request is received */

            l_t_DmaCfg.size           = SGM_k_STREAM_BUF_SIZE;

            l_t_DmaCfg.count          = sgm_k_STREAM_BUF_COUNT;

            l_t_DmaCfg.validSckCount  = sgm_k_SOCKET_COUNT;

            l_t_DmaCfg.prodSckId[0]   = sgm_k_PRODUCER_PPORT_SOCKET_0;

            l_t_DmaCfg.prodSckId[1]   = sgm_k_PRODUCER_PPORT_SOCKET_1;

            l_t_DmaCfg.consSckId[0]   = sgm_k_EP_VIDEO_CONS_SOCKET;

            l_t_DmaCfg.dmaMode        = CY_U3P_DMA_MODE_BYTE;

            l_t_DmaCfg.notification   = CY_U3P_DMA_CB_PROD_EVENT | CY_U3P_DMA_CB_CONS_EVENT;

            l_t_DmaCfg.cb             = sgm_cb_ManageStream;

            l_t_DmaCfg.prodHeader     = SGM_k_PROD_HEADER;

            l_t_DmaCfg.prodFooter     = SGM_k_PROD_FOOTER;

            l_t_DmaCfg.consHeader     = 0;

            l_t_DmaCfg.prodAvailCount = 1;


            l_t_Status = CyU3PDmaMultiChannelCreate(&sgm_t_StreamTransferHandle, CY_U3P_DMA_TYPE_MANUAL_MANY_TO_ONE, &l_t_DmaCfg);


            if (CY_U3P_SUCCESS == l_t_Status)



                 l_t_Status = CyU3PDmaMultiChannelReset(&sgm_t_StreamTransferHandle);






            We do not have any problem at this point.

            Later in code, we do a reset and get the Bad argument error.


            As you suggest, we add debug to check Start.sig and End.sig:

            INFO ( Camled:ThreadRspEvt ) : Start ThreadRspEvt

            INFO ( Camled:ThreadRspEvt ) : CX3;[30];52 TRC_USBDebugInStart: Trace enabled

            INFO ( Camled:ThreadRspEvt ) : CX3;[4];201 CyCx3AppUSBEventCB: CyCx3AppUSBEventCB 4 1

            INFO ( Camled:ThreadRspEvt ) : CX3;[30];253 sgm_t_InitializeStreamTransfer: CyU3PDmaMultiChannelReset SUCCESS returns 0x0 startSig=4D4C4348 endSig=454E4443

            INFO ( Camled:ThreadRspEvt ) : CX3;[4];283 CyCx3AppUSBEventCB: CyCx3AppUSBEventCB 5 1

            INFO ( Camled:ThreadRspEvt ) : CX3;[30];491 sgm_t_InitGenStream: sgm_t_InitGenStream SUCCESS

            ERROR ( Camled:ThreadRspEvt ) : CX3;[30];501 SCG_t_SetSensorSleep: Stream control 0

            INFO ( Camled:ThreadRspEvt ) : CX3;[30];501 VIM_t_ThreadStreamManager: SGM Wait Event.

            INFO ( Camled:StartVideo ) : [START_VIDEO] Gain = 2 ; Shutter = 20 ; Lighting = 50 ; Nb_Lights = 15

            INFO ( Camled:ThreadRspEvt ) : CX3;[1];17014 rfh_cb_ProcessRecFrame: RFH_CMD_STREAM_START

            INFO ( Camled:ThreadRspEvt ) : CX3;[30];17014 VIM_t_ThreadStreamManager: SGM_k_START_VIDEO_EVENT

            INFO ( Camled:ThreadRspEvt ) : CX3;[30];17076 vim_t_StartStream: Start stream

            ERROR ( Camled:ThreadRspEvt ) : CX3;[30];17076 sgm_t_SetStreamTransfer: CyU3PDmaMultiChannelReset returns 0x40 startSig=0 endSig=454E4443


            The first print is OK (in initialization function) but the second one is KO, the start.sig is 0.

            I guess it is not normal, but I don't understand how this value changed and how to avoid it?


            Thank you.

            Best regards,



            • 3. Re: CX3 DMA issue

              Hi Kandlagunta_R36,


              Do you have any test to do to understand why StartSig is modified ?

              We tried to find when it is modified, without any success yet.


              Thank you,

              Best regards,


              • 4. Re: CX3 DMA issue



                Please check CyU3PDmaMultiChannelIsValid before doing the reset.

                Use this API at some places of code and check where exactly the startsig got changed.


                CyU3PDmaMultiChannelIsValid validates the handle, startsig and endsig.


                I can see that you have set the l_t_DmaCfg.prodAvailCount to 1 while creating the dma channel. Can you please set this Zero and see?