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.

AM6548: About channel Teardown during data transfer with UDMA

Part Number: AM6548

Memory-to-memory transfer (block transfer) is performed using UDMA of AM65x.
At that time, when the channel is teardown during data transfer, the channel cannot be used continuously even if the channel is enabled again.

It works fine in the following cases.
1. Channel open (channel configuration)
2. Channel enabled
3. Data transfer (M2M block transfer)
4. Channel disabled (Teardown after all data transfer is completed)
5. Repeat steps 2 to 4

Does not work properly in the following cases
1. Channel open (channel configuration)
2. Channel enabled
3. Data transfer (M2M block transfer)
 ・ Set multiple transfer data in the free ring queue (example: 64 requests)
 ・ Start data transfer (64 requests are set to DoorBell)
4. Channel disabled during data transfer
 ・ Teardown for TX channel
 ・ After Teardown, re-enable the channel
5. Channel disabled
 ・ Teardown does not work properly.(Polling the EN bit of UDMA_TRT_CTL_j Register defined in UDMASS_UDMAP0_CFG_TCHANRT, but not disabled)

As a post-processing of Teardown during data transfer, the unprocessed request in the free ring queue is popped..
Is there any other post-processing required after Teardown during data transfer?

  • Hi Kazuya-san,

    Does the chDisable API return fine? What's the timeout value set in this API?

    Regards,

    Brijesh

  • Hi, Brijesh

    The timeout is set to 1 second.

    Channel Disable in step 4 is working normally.
    The EN bit is cleared after Teardown.

    Step 5 does not work.
    As follows:
    Disable (step 4-1) → Enable (step 4-2) → Disable (step 5)
    In this case, step 5 times out.

    Also, after STEP4, nothing happens even if DMA transfer is performed again.
    Channel seems not working after Teardown during DMA transfer.

    Regards,

    K.Shigesada

  • Hi Shigesada,

    Are you passing Teardown completion queue ring params, (similar to Completion queue ring params) during 'Udma_chOpen'?

    If not, please try passing 'tdCqRingPrms.ringMem', 'tdCqRingPrms.ringMemSize', 'tdCqRingPrms.elemCnt'.

    Also, Register teardown ring completion event (eventType = UDMA_EVENT_TYPE_TEARDOWN_PACKET) and in the callback function dequeue response from teardown completion ring using 'Udma_chDequeueTdResponse'

    Regards,

    Don Dominic

  • Hi, Dominic

    I've done all the steps you say.
    This issue occurs during Teardown during DMA transfer.

    Please check the processing flow that causes the problem below.

      

    The software cannot DMA transfer with the channel enabled after step 9.
    Or, it cannot be repeatedly enabled / disabled (tear down) for the channel.
    The hardware becomes unresponsive to these processes.

    In the non-DMA transfer state, everything works fine even after Teardown.

    Is there any post-processing missing in the above cases?

    Regards,

    K.Shigesada

  • Hi Shigesada,

    Sorry for the delayed response!

    In step 9, How do you dequeue the unprocessed descriptors from the free queue?

    Dequeuing from a ring (free queue) should be performed only using the 'Udma_ringFlushRaw' API.
    Note: This API will only dequeue one descriptor at a time. The user is expected to call this API repeatedly until all unprocessed descriptors are dequeued.
    You can refer to pdk/packages/ti/drv/udma/examples/udma_memcpy_test/udma_memcpy_test.c, in which the API is repeatedly called until it returns timeout error(which indicates no more unprocessed descriptors left in the free queue)
    If you are already using this API and dequeuing all the unprocessed descriptors, Please share the following RT Register values of Free Queue Ring (chHandle->fqRing->pRtRegs->) after this operation.
    1. OCC
    2. INDX
    3. HWOCC
    4. HWINDX

    Regards,

    Don Dominic

  • Hi, Dominic

    We are developing drivers without using PDK.
    However, it implements the same processing as the'Udma_ringFlushRaw' API.

    The ring counter when dequeue processing is performed is described below.
    This use case puts 64 requests in the free queue, and commits all 64 requests (64 is set in the DoorBell register).#The maximum number of free queue entries is 64.
    Perform Teardown during DMA transfer from another software thread.
    16 requests have completed DMA transfer and 48 requests have not been processed.
    In this state, it is the result of repeatedly popping unprocessed requests from the free queue.

    (I think that it's working properly.)

    OCC IDX HWOCC HWIDX
    47 0 47 17
    46 0 46 18
    45 0 45 19
    44 0 44 20
    43 0 43 21
    42 0 42 22
    41 0 41 23
    40 0 40 24
    39 0 39 25
    38 0 38 26
    37 0 37 27
    36 0 36 28
    35 0 35 29
    34 0 34 30
    33 0 33 31
    32 0 32 32
    31 0 31 33
    30 0 30 34
    29 0 29 35
    28 0 28 36
    27 0 27 37
    26 0 26 38
    25 0 25 39
    24 0 24 40
    23 0 23 41
    22 0 22 42
    21 0 21 43
    20 0 20 44
    19 0 19 45
    18 0 18 46
    17 0 17 47
    16 0 16 48
    15 0 15 49
    14 0 14 50
    13 0 13 51
    12 0 12 52
    11 0 11 53
    10 0 10 54
    9 0 9 55
    8 0 8 56
    7 0 7 57
    6 0 6 58
    5 0 5 59
    4 0 4 60
    3 0 3 61
    2 0 2 62
    1 0 1 63
    0 0 0 0

    The PDK only commits with one request, but are you trying multiple request commits (and Teardown)?

    regards.

    K.Shigesada

  • Hi Shigesada,

    After dequeueing all the unprocessed descriptors from the free queue ring, resetting the ring is recommended for returning a ring to a known state.

    Can you try this?

    Reset the ring by writing to ring's BA_LO, BA_HI, or SIZE register.
    Regards
    Don Dominic
  • Hi, Dominic

    Thank you for your reply.


    As a result of trying ring reset, channel enable / disable worked fine.

    I will confirm one below.
    In my understanding, resetting the ring is only applicable to SR1.0 as the PDK (TI-SDK-7.0.0) said.

    [function - Udma_ringReset]

    regVal = CSL_REG32_RD(&drvHandle->raRegs.pGlbRegs->REVISION);
    if(!((CSL_FEXT(regVal, RINGACC_GCFG_REVISION_REVMAJ) > 1U) ||
      (CSL_FEXT(regVal, RINGACC_GCFG_REVISION_REVMIN) > 0U) ||
      (CSL_FEXT(regVal, RINGACC_GCFG_REVISION_REVRTL) > 19U)))
      {・・・

    However, in reality, it had to be applied to SR2.0 as well. This is correct?

    Also, should I apply the process of resetting the ring whenever the channel is initialized?

  • Hi Shigesada,

    After dequeueing the unprocessed descriptors from the free queue ring, resetting the ring is strongly suggested as part of the procedure for returning a ring to a known state.

    After channel initialization during ring configuration for setting the RING_BA_LO/RING_BA_HI/RING_SIZE registers, the ring will get initialized properly.

    Regards

    Don Dominic

  • Hi, Dominic

    Thank you for your reply.

    The problem has been resolved.
    I will reset the ring during channel configuration and Teardown.

    Regards.

    K.Shigesada