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.

AIF2 AT Event Generation problem

Hi  Ti engineers,

    Now I'm using the AIF2 module in LTE , CPRI mode. I want to connect the AIF2 with the FFTC by using the AT event for UL LTE symbol data.  When  AIF2 has fully received  each AxCs one symbol data, I need to get a AT event to trigger the EDMA to  handle all the AxC data.

    But now I'm compusing about  setup the AT Event register.  How can I make sure that when the event is generated, 

the AIF fully received all AxCs symbol data because of the fiber len?   when the timer start to count , maybe the data is just on the fiber.  I can only caculate the fiber delay and add it to the offset  to make sure the event is correct?    Is this the only way for my problem?

 Thanks for your reply,

Regards,

ziyang 

  • Hi Ziyang,

    From your previous post, I understand that you are using C6670. Also confirm the packages used and its version to support you better.

    Thanks.

  • Yes , I am using C6670 multicore dsp for LTE ENode develop.

  • Hi zi yang,

    your assumption is correct. there is a to solve this problem.

    Use UL RAD timer and set initial delay to (Pi + internal process delay (see user guide) + DMA delay) and trigger symbol event from this UL RAD timer and it will generate correct symbol trigger once the symbol has fully arrived.

    DL RAD timer can be used for down link (egress side) timing and this is why we created three radio timers.

    for internal delay calculation, please see AIF2 UG timing chapter more carefully.

    Regards,

    Albert 

  • Hi Albert,  thanks for your reply.

    I think the AT event is too hard to config now because I have to caculate the precise delay, so I want to use the QMSS PDSP event to get the event.  When the AIF2 rxq receive enough desc, the pdsp will trigger a event and then start the EDMA module. 

    Can I make sure  that the the first symbol I get from the AIF2 rxQ is symbol 0 ? I need to confirm this to config the EMDA module.

    Regards,

    ziyang

  • Hi Ziyang,

    sorry to hear that the AT was too hard for you to use. one LTE symbol time is 67 us, so we think the minor delay or time difference doesn't make serious issue. anyway, QMSS PDSP accumulator event is also a good solution to you.

    your first received symbol from RxQ should be a symbol 0, because AIF2 start receiving from symbol 0 as soon as RM status is in frame sync status. hope this could help to you.

    Regards,

    Albert

  • Hi Albert,

    Sorry for that I may not describe my situation very well.  The AT timer_boundary_strobe concept is hard for me to understand but it is not the point actually.  Our manager want our LTE eNodeB that can adjust the fiber delay automatically.  It means we may change the fiber len and do not need to set the fiber delay each time.  In my opinion,  I need to start the AIF2 first and get the Pi value each time,  then stop it and use the Pi to config the AT event module so it can works fine with the EDMA module, and then restart the AIF2.  This whole process is so complex that I just want to use the QMSS PDSP accumulator event. 

    Also, thank you for your reply,  it helps me a lot.

    Regards,

    Ziyang

  • Hi Albert,

    I have configed the AIF2 and EDMA module now and it's nearly finished. But I just find a problem that I do not know how to map the QMSS PDSP accumulator event  to trigger the EDMA. Do you konw what to do and give me a brief guied? Thank you.

    Regards,

    Ziyang

  • Hi Ziyang,

    Sorry for my late response. I found this request today.

    Please see my attached example code for your information.

    Hope this could helpful to you.

    Regards,

    Albert

    /****************************************************************************\
     *           Copyright (C) 2009 Texas Instruments Incorporated.             *
     *                           All Rights Reserved                            *
     *                                                                          *
     * GENERAL DISCLAIMER                                                       *
     * -------------------------------------------------------------------      *
     * All software and related documentation is provided "AS IS" and without   *
     * warranty or support of any kind and Texas Instruments expressly disclaims*
     * all other warranties, express or implied, including, but not limited to, *
     * the implied warranties of merchantability and fitness for a particular   *
     * purpose.  Under no circumstances shall Texas Instruments be liable for   *
     * any incidental, special or consequential damages that result from the    *
     * use or inability to use the software or related documentation, even if   *
     * Texas Instruments has been advised of the liability.                     *
     ****************************************************************************
     *                                                                          *
     * Written by :                                                             *
     *            Albert Bae                                                    *
     *            Texas Instruments                                             *
     *            15 Nov, 2010                                                 *
     *                                                                          *
     ***************************************************************************/
    #include <stdio.h>
    #include <stdlib.h>
    #include <stdint.h> 
    
    /* QMSS LLD include */
    #include <ti/drv/qmss/qmss_drv.h>
    #include <ti/drv/qmss/qmss_firmware.h>
    
    /* Navigator LLD include */
    #include <ti/drv/cppi/cppi_drv.h>
    #include <ti/drv/cppi/cppi_desc.h>
    
    /* CSL RL includes */
    #include <ti/csl/csl_chip.h>
    /* INTC CSL include */
    #include <ti/csl/src/intc/csl_intc.h>
    /* AIF2 CSL include */
    #include "Aif2_config.h"
    #include "psc_util.h"
       
    /* Define queues for common FDQs */
    #define HOST_TX_FDQ            2000
    #define HOST_RX_FDQ            2001
    
    /* These are for the AIF2 test */
    #define HOST_TX_Q              512
    
    #define NUM_HOST_DESC               32
    #define SIZE_HOST_DESC              64
    #define SIZE_DATA_BUFFER            256
    #define NUM_PACKETS                 8
    
    #pragma DATA_SECTION(host_region,".intData_sect")//use MSMC memory for test mode
    #pragma DATA_ALIGN (host_region, 16)
    Uint8   host_region[32 * 64]; 
    #pragma DATA_SECTION(tx_buffer,".intData_sect")//use MSMC memory for test mode
    Uint8   tx_buffer[16 * 256]; 
    #pragma DATA_SECTION(rx_buffer,".intData_sect")//use MSMC memory for test mode
    Uint8   rx_buffer[16 * 256]; 
    #pragma DATA_SECTION(DataTempBuff,".intData_sect")//use MSMC memory for test mode  
    Uint32  DataTempBuff[128];
    Uint8   *rxBuffPtr;
    
    Qmss_AccCmdCfg          cfg;
    /* List address for accumulator - twice the number of entries for Ping and Pong page */
    #pragma DATA_SECTION(hiPrioList,".intData_sect")//use MSMC memory for test mode
    #pragma DATA_ALIGN (hiPrioList, 16)
    Uint32  hiPrioList[(NUM_PACKETS + 1) * 2];
    
    /* Intc variable declarartion */
    CSL_IntcObj    intcObj[2];
    CSL_IntcHandle   hIntc[2];
    CSL_IntcEventHandlerRecord  EventHandler[2];
    CSL_IntcGlobalEnableState state;
    
    /* MNavigator handle for this test */
    Cppi_Handle             cppiHnd;
    Cppi_ChHnd              rxChHnd, txChHnd;
    Qmss_QueueHnd           txQueHnd, rxQueHnd, freeQueHnd, txFreeQueHnd;
    Cppi_FlowHnd            rxFlowHnd;
    /* PKTDMA configuration */
    Cppi_CpDmaInitCfg       cpdmaCfg;
    /* Tx channel configuration */
    Cppi_TxChInitCfg        txChCfg;
    /* Rx channel configuration */
    Cppi_RxChInitCfg        rxChCfg;
    /* Rx flow configuration */
    Cppi_RxFlowCfg          rxFlowCfg;
    /* QMSS configuration */
    Qmss_InitCfg            qmssInitConfig;
    /* Memory region configuration information */
    Qmss_MemRegInfo         hostMemInfo;
    /* Core number */
    Uint32                  coreNum;
    Cppi_Desc               *hostDescPtr[8];
    
    /* qmss and cppi global config parameters */
    extern Qmss_GlobalConfigParams  qmssGblCfgParams;
    extern Cppi_GlobalConfigParams  cppiGblCfgParams[CPPI_MAX_CPDMA];
    
    /* Global structures and variables  */
    CSL_Aif2Obj Aif2Obj;// Aif2 CSL object
    CSL_Aif2Handle hAif2;// Aif2 handle 
    Bool ctrlArg; // Ctrl Argument;
    
    CSL_Aif2Context Aif2Context;//Aif2 context
    CSL_Aif2Param  aif2Param;//AIF2 module specific parameters
    CSL_Status status; // CSL status
       
    CSL_Aif2Setup               aif2Setup;//Aif2 HW setup
    CSL_Aif2LinkSetup           linkSetup;// Setup for links 
    CSL_Aif2GlobalSetup         globalSetup;// global config for AIF2 
    CSL_Aif2CommonSetup         commonSetup; // Setup for common params
       
    CSL_Aif2SdCommonSetup       SdCommonSetup;//SERDES common setup
    CSL_Aif2PdCommonSetup       PdCommonSetup;//PD common setup
    CSL_Aif2PeCommonSetup       PeCommonSetup;//PE common setup
    CSL_Aif2IngrDbSetup         IngrDbSetup;// Ingress data buffer setup 
    CSL_Aif2EgrDbSetup          EgrDbSetup;// Egress data buffer setup 
    CSL_Aif2AdCommonSetup       AdCommonSetup;// Aif2 DMA common setup 
    CSL_Aif2AtCommonSetup       AtCommonSetup; // Aif2 Timer common  setup 
    CSL_Aif2AtEventSetup        AtEventSetup; // Aif2 Timer external and internal event  setup 
    CSL_Aif2AtCountObj          PhyTimerTc;// AT Phy Terminal Count setup
    CSL_Aif2AtCountObj          RadTimerTc;// AT Rad Terminal Count setup
    CSL_Aif2AtCountObj          PhyTimerInit;// AT Phy Init value setup
    CSL_Aif2AtCountObj          RadTimerInit;// AT Rad Init value setup
       
    CSL_Aif2CommonLinkSetup     ComLinkSetup; // Aif2 link common setup 
    CSL_Aif2SdLinkSetup         SdLinkSetup; //SERDES link setup
    CSL_Aif2RmLinkSetup         RmLinkSetup; //RM link setup
    CSL_Aif2TmLinkSetup         TmLinkSetup; //TM link setup
    CSL_Aif2PdLinkSetup         PdLinkSetup; //PD link setup
    CSL_Aif2PeLinkSetup         PeLinkSetup; //PE link setup
    CSL_Aif2RtLinkSetup         RtLinkSetup; //RT link setup
    CSL_Aif2AtLinkSetup         AtLinkSetup; // Aif2 timer link setup (Pi, Delta, PE signal) 
    
    volatile unsigned int int4_result = 0, int5_result = 0;
    
    interrupt void int4_isr(){
        int i;
        
        /* Push descriptor to AIF2 Tx queue */
        if(int4_result == 1){
          for(i = 0;i < 8;i++)
          Qmss_queuePushDescSize (txQueHnd, (Uint8 *) hostDescPtr[i], 64);// 64 byte DESC_SIZE is mendatory for AIF2
        }
        
        int4_result++;
    }
    
    interrupt void int5_isr(){
    	int channel = 0; //accumulator channel num 
    	Qmss_ackInterrupt (channel, 1);
        Qmss_setEoiVector (Qmss_IntdInterruptType_HIGH, channel);
    
        /* Clear the Interrupt */
        CSL_intcHwControl(hIntc[1],CSL_INTC_CMD_EVTCLEAR,NULL);
        int5_result++;
    }
    
    void Init_data_buffer(void){
    	int i;
    	/* Fill in some data into temp data buffer */
        for (i = 0; i < 128; i++) DataTempBuff[i] = (Uint32)(0x00010000 + i);
        
    	for (i = 0; i < 8; i++){//initialize the Tx buffers
    	memcpy((void *)&tx_buffer[i * 512], (void *)&DataTempBuff[0], 512);//initialize the Tx host buffers
    	}
        memset(rx_buffer, 0x0, 512 * 8);//initialize the Rx buffers
    }
    
    void Intc_config(void)
    {
       CSL_IntcParam    vectId;
       CSL_IntcContext  context;
       //!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!//
       //! GEM0 Intc Configuration              !//
       //!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!//
       /* Setup the global Interrupt */
       context.numEvtEntries = 8;    
       context.eventhandlerRecord = EventHandler; 
       CSL_intcInit(&context);
       /* Enable NMIs  */
       CSL_intcGlobalNmiEnable();
       /* Enable Global Interrupts  */
       CSL_intcGlobalEnable(&state);
       
       /* VectorID for the Global Edma Event  */
       vectId = CSL_INTC_VECTID_4;
       
       /* Opening a handle for the Fsync->EDMA Interrupt Event */                                      
       hIntc[0]   = CSL_intcOpen(&intcObj[0],
                               AIF2_EVENT7_INTSEL_MAP, // Event 7
                               &vectId,
                               NULL);
       //Hook the ISRs
       CSL_intcHookIsr(vectId,  &int4_isr);
      
       /* VectorID for the General Event  */
       vectId = CSL_INTC_VECTID_10;
       /* Opening a handle for the QMSS Hi priority accumulator Interrupt Event */                                      
       hIntc[1]   = CSL_intcOpen(&intcObj[1],
                               FIRST_HI_GEM_EVENT, // Hi priority GEM Event for Accumulator
                               &vectId,
                               NULL);
       //Hook the ISRs
       CSL_intcHookIsr(vectId,  &int5_isr);
       
       // Clear the Interrupt    
       CSL_intcHwControl(hIntc[0], CSL_INTC_CMD_EVTCLEAR,  NULL);
       CSL_intcHwControl(hIntc[1], CSL_INTC_CMD_EVTCLEAR,  NULL);
       //Enable the Event & the interrupt 
       CSL_intcHwControl(hIntc[0], CSL_INTC_CMD_EVTENABLE,  NULL);
       CSL_intcHwControl(hIntc[1], CSL_INTC_CMD_EVTENABLE,  NULL);
    	
    }
    
    void MNav_config(void){
        Qmss_Result             result;
        Uint32                  numAllocated,i;
        Uint8                   isAllocated;
        Cppi_DescCfg            descCfg;
        Qmss_Queue              queInfo;
        
        /* Get the core number. */
        coreNum = CSL_chipReadReg(CSL_CHIP_DNUM); 
        /* Initialize the heap in shared memory for CPPI data structures */
        initCppiMem ();// init MNavigator memory
        initQmssMem ();// init QMSS memory
        
        memset ((void *) &qmssInitConfig, 0, sizeof (Qmss_InitCfg));
        /* Use Internal LinkRAM  */
        qmssInitConfig.linkingRAM0Base = 0;
        qmssInitConfig.linkingRAM0Size = 0;
        qmssInitConfig.linkingRAM1Base = 0;
        qmssInitConfig.maxDescNum      = NUM_HOST_DESC;
        /* Use PDSP firmware for little endian */
        qmssInitConfig.pdspFirmware[0].pdspId = Qmss_PdspId_PDSP1;
        qmssInitConfig.pdspFirmware[0].firmware = &acc48_le;
        qmssInitConfig.pdspFirmware[0].size = sizeof (acc48_le);
    
        /* Initialize Queue Manager SubSystem */
        result = Qmss_init (&qmssInitConfig, &qmssGblCfgParams);
        if (result != QMSS_SOK)
        {
            printf ("Error Core %d : Initializing Queue Manager SubSystem error code : %d\n", coreNum, result);
            return;
        }
        /* Start Queue Manager SubSystem */
        result = Qmss_start ();
        if (result != QMSS_SOK)
        printf ("Core %d : Error starting Queue Manager error code : %d\n", coreNum, result);
    
        /* Initialize MNavigator LLD */
        result = Cppi_init (&cppiGblCfgParams[0]);
        if (result != CPPI_SOK)
        printf ("Error Core %d : Initializing CPPI LLD error code : %d\n", coreNum, result);
    
        /* Set up AIF2 PKTDMA configuration */
        memset ((void *) &cpdmaCfg, 0, sizeof (Cppi_CpDmaInitCfg));
        cpdmaCfg.dmaNum = Cppi_CpDma_AIF_CPDMA;
    
        /* Open AIF2 PKTDMA */
        cppiHnd = (Cppi_Handle) Cppi_open (&cpdmaCfg);
        if (cppiHnd == NULL)
        {
            printf ("Error Core %d : Initializing QMSS CPPI CPDMA %d\n", coreNum, cpdmaCfg.dmaNum);
            return;
        }
    
        /* Setup memory region for monolithic descriptors */
        memset ((void *) &host_region, 0, SIZE_HOST_DESC * NUM_HOST_DESC);
        hostMemInfo.descBase = (Uint32 *) &host_region[0];
        hostMemInfo.descSize = SIZE_HOST_DESC;
        hostMemInfo.descNum = NUM_HOST_DESC;
        hostMemInfo.manageDescFlag = Qmss_ManageDesc_MANAGE_DESCRIPTOR;
        hostMemInfo.memRegion = Qmss_MemRegion_MEMORY_REGION0;
        hostMemInfo.startIndex = 0;
    
        result = Qmss_insertMemoryRegion (&hostMemInfo);
        if (result < QMSS_SOK)
        printf ("Error Core %d : Inserting memory region %d error code : %d\n", coreNum, hostMemInfo.memRegion, result);
        
        /* Setup the descriptors for transmit free queue */
        memset(&descCfg, 0, sizeof(descCfg));
        descCfg.memRegion = Qmss_MemRegion_MEMORY_REGION0;
        descCfg.descNum = NUM_PACKETS;// 8 descriptors for this test
        descCfg.destQueueNum = HOST_TX_FDQ;
        descCfg.queueType = Qmss_QueueType_GENERAL_PURPOSE_QUEUE;
        descCfg.initDesc = Cppi_InitDesc_INIT_DESCRIPTOR;
        descCfg.descType = Cppi_DescType_HOST;
        descCfg.epibPresent = Cppi_EPIB_NO_EPIB_PRESENT;
        /* Descriptor should be recycled back to Queue Number 2000 */
        descCfg.returnQueue.qMgr = 0;
        descCfg.returnQueue.qNum = HOST_TX_FDQ;
        
        /* Initialize the descriptors and push to free Queue */
        if ((txFreeQueHnd = Cppi_initDescriptor (&descCfg, &numAllocated)) < 0)
    	{
            printf ("Error Core %d : Initializing Tx descriptor error code: %d \n", coreNum, txFreeQueHnd);
    		return;
    	}
    
        /* Setup the descriptors for receive free queue */
        memset(&descCfg, 0, sizeof(descCfg));
        descCfg.memRegion = Qmss_MemRegion_MEMORY_REGION0;
        descCfg.descNum = NUM_PACKETS; // 8 descriptors for this test
        descCfg.destQueueNum = HOST_RX_FDQ;
        descCfg.queueType = Qmss_QueueType_GENERAL_PURPOSE_QUEUE;
        descCfg.initDesc = Cppi_InitDesc_INIT_DESCRIPTOR;
        descCfg.descType = Cppi_DescType_HOST;
        descCfg.epibPresent = Cppi_EPIB_NO_EPIB_PRESENT;
        descCfg.returnQueue.qMgr = QMSS_PARAM_NOT_SPECIFIED;
        descCfg.returnQueue.qNum = QMSS_PARAM_NOT_SPECIFIED;
        
        /* Initialize the descriptors and push to free Queue */
        if ((freeQueHnd = Cppi_initDescriptor (&descCfg, &numAllocated)) < 0)
    	{
            printf ("Error Core %d : Initializing Rx descriptor error code: %d \n", coreNum, freeQueHnd);
    		return;
    	}
    
        /* Setup Rx descriptors with receive buffers */
        for (i = 0; i < numAllocated; i++)
        {
            Ptr dataPtr = rx_buffer + i * SIZE_DATA_BUFFER;
            /* Get a descriptor */
            if ((hostDescPtr[0] = (Cppi_Desc *) Qmss_queuePop (freeQueHnd)) == NULL)
            {
                printf ("Error Core %d : Getting descriptor from Queue Number\n", coreNum, freeQueHnd);
                return;
            }
            /* Add data buffer */
            Cppi_setData (Cppi_DescType_HOST, hostDescPtr[0], (Uint8 *)dataPtr, SIZE_DATA_BUFFER);
            /* Save original buffer information */
            Cppi_setOriginalBufInfo (Cppi_DescType_HOST, hostDescPtr[0], (Uint8 *)dataPtr, SIZE_DATA_BUFFER);
    
            /* Push descriptor to Rx free queue */
            Qmss_queuePushDesc (freeQueHnd, (Uint32 *) hostDescPtr[0]);
        }
    	
        /* Set up AIF2 PKTDMA Rx Channel parameters */
        rxChCfg.channelNum = 0;// PKTDMA channel 0 (should be matched with AIF2 DB channel)
        rxChCfg.rxEnable = Cppi_ChState_CHANNEL_DISABLE;
        
        /* Open Rx Channel */
        rxChHnd = (Cppi_ChHnd) Cppi_rxChannelOpen (cppiHnd, &rxChCfg, &isAllocated);
        if (rxChHnd == NULL)
        {
            printf ("Error Core %d : Opening Rx channel : %d\n", coreNum, rxChCfg.channelNum);
            return;
        }
        
        /* Set up Tx Channel parameters */
        txChCfg.channelNum = 0;// PKTDMA channel 0 (should be matched with AIF2 DB channel)
        txChCfg.priority = 0;
        txChCfg.filterEPIB = 0;
        txChCfg.filterPS = 0;
        txChCfg.aifMonoMode = 0;
        txChCfg.txEnable = Cppi_ChState_CHANNEL_DISABLE;
        
        /* Open Tx Channel */
        txChHnd = (Cppi_ChHnd) Cppi_txChannelOpen (cppiHnd, &txChCfg, &isAllocated);
        if (txChHnd == NULL)
        {
            printf ("Error Core %d : Opening Tx channel : %d\n", coreNum, txChCfg.channelNum);
            return;
        }
        
        /* Opens transmit queue. This is the AIF2 specified Tx queue */
        if ((txQueHnd = Qmss_queueOpen (Qmss_QueueType_AIF_QUEUE, HOST_TX_Q, &isAllocated)) < 0)
    	{
            printf ("Error Core %d : Opening Transmit Queue Number\n", coreNum);
    		return;
    	}
        else
            printf ("Core %d : Transmit Queue Number : %d opened\n", coreNum, txQueHnd);
    
        /* Opens receive queue (General purpose queue)*/
        if ((rxQueHnd = Qmss_queueOpen (Qmss_QueueType_HIGH_PRIORITY_QUEUE, QMSS_PARAM_NOT_SPECIFIED, &isAllocated)) < 0)
    	{
            printf ("Error Core %d : Opening Receive Queue Number\n", coreNum);
            return;
    	}
        else
            printf ("Core %d : Receive Queue Number : %d opened\n", coreNum, rxQueHnd);
    
        printf ("Core %d : Rx Free Queue Number : %d opened\n", coreNum, freeQueHnd);
        printf ("Core %d : Transmit Free Queue Number : %d opened\n", coreNum, txFreeQueHnd);
    
        Qmss_configureAccTimer (Qmss_PdspId_PDSP1, 3500);// configure accumulator timer delay to 20 us
    
        // program the high priority accumulator 
        memset ((void *) &hiPrioList, 0, sizeof (hiPrioList));
        cfg.channel = 0;
        cfg.command = Qmss_AccCmd_ENABLE_CHANNEL;
        cfg.queueEnMask = 0;
        cfg.listAddress = (Uint32) hiPrioList; // Should be global if reading on another core
        // Get queue manager and queue number from handle 
        queInfo = Qmss_getQueueNumber (rxQueHnd);
        cfg.queMgrIndex = queInfo.qNum;
        cfg.maxPageEntries = NUM_PACKETS + 1 ;
        cfg.timerLoadCount = 0;
        cfg.interruptPacingMode = Qmss_AccPacingMode_NONE;
        cfg.listEntrySize = Qmss_AccEntrySize_REG_D;
        cfg.listCountMode = Qmss_AccCountMode_ENTRY_COUNT;
        cfg.multiQueueMode = Qmss_AccQueueMode_SINGLE_QUEUE;
        
        if ((result = Qmss_programAccumulator (Qmss_PdspId_PDSP1, &cfg)) != QMSS_ACC_SOK)
    	{
           printf ("Error Core %d : Programming high priority accumulator for channel : %d queue : %d error code : %d\n",
                            coreNum, cfg.channel, cfg.queMgrIndex, result);
    		return;
    	}
    	
        /* Setup Rx flow parameters */
        memset ((void *) &rxFlowCfg, 0, sizeof (Cppi_RxFlowCfg));
        rxFlowCfg.flowIdNum = 0;// flow ID number should be matched with AIF2 DB channel number
        /* Get queue manager and queue number from handle */
        queInfo = Qmss_getQueueNumber (rxQueHnd);
        rxFlowCfg.rx_dest_qnum = queInfo.qNum;
        rxFlowCfg.rx_dest_qmgr = queInfo.qMgr;
        rxFlowCfg.rx_desc_type = Cppi_DescType_HOST; 
        /* Get queue manager and queue number from handle */
        queInfo = Qmss_getQueueNumber (freeQueHnd);
        rxFlowCfg.rx_fdq0_sz0_qnum = queInfo.qNum;
        rxFlowCfg.rx_fdq0_sz0_qmgr = queInfo.qMgr;
        rxFlowCfg.rx_fdq1_qnum = queInfo.qNum;//for second linked buffer
        rxFlowCfg.rx_fdq1_qmgr = queInfo.qMgr;
    
        /* Configure Rx flow */
        rxFlowHnd = (Cppi_FlowHnd) Cppi_configureRxFlow (cppiHnd, &rxFlowCfg, &isAllocated);
        if (rxFlowHnd == NULL)
        {
            printf ("Error Core %d : Opening Rx flow : %d\n", coreNum, rxFlowCfg.flowIdNum);
            return;
        }
      
        /* Disable PKTDMA module loopback */
        Cppi_setCpdmaLoopback (cppiHnd, 0);
        /* Enable transmit and receive channel */
        Cppi_channelEnable (txChHnd);
        Cppi_channelEnable (rxChHnd);
            
        /***** Send out 8 packets. pop 8 Tx free descriptors and push into the AIF2 Tx Queue  ***************/
        for (i = 0; i < NUM_PACKETS; i++)
        {
            /* Get a free descriptor */
            if ((hostDescPtr[i] = (Cppi_Desc *) Qmss_queuePop (txFreeQueHnd)) == NULL)
            {
               printf ("Error Core %d : Getting descriptor from Queue Number %d \n", coreNum, txFreeQueHnd);
               return;
            }   
                 /* Add data buffer */
                 Cppi_setData (Cppi_DescType_HOST, hostDescPtr[i], (Uint8 *) &tx_buffer[i * 512], SIZE_DATA_BUFFER);
             
                 Cppi_setOriginalBufInfo (Cppi_DescType_HOST, hostDescPtr[i], (Uint8 *) &tx_buffer[i * 512], SIZE_DATA_BUFFER);
            
                 /* Set total packet length in chain */
            Cppi_setPacketLen (Cppi_DescType_HOST, hostDescPtr[i], SIZE_DATA_BUFFER);//packet length is 512 byte
            
                 /* Push descriptor to AIF2 Tx queue is done in ISR */
            }
           
    }
    
    void Aif2_config(void)
    {
       int i; 
       
       /************ Initialize Aif2 structures to avoid unwanted configuration ************************************************/ 
       memset(&globalSetup, 0, sizeof(globalSetup));
       memset(&linkSetup, 0, sizeof(linkSetup));
       memset(&commonSetup, 0, sizeof(commonSetup));
       
       memset(&SdCommonSetup, 0, sizeof(SdCommonSetup));
       memset(&PdCommonSetup, 0, sizeof(PdCommonSetup));
       memset(&PeCommonSetup, 0, sizeof(PeCommonSetup));
       memset(&IngrDbSetup, 0, sizeof(IngrDbSetup));
       memset(&EgrDbSetup, 0, sizeof(EgrDbSetup));
       memset(&AdCommonSetup, 0, sizeof(AdCommonSetup));
       memset(&AtCommonSetup, 0, sizeof(AtCommonSetup));
       memset(&AtEventSetup, 0, sizeof(AtEventSetup));
       memset(&PhyTimerInit, 0, sizeof(PhyTimerInit));
       memset(&RadTimerInit, 0, sizeof(RadTimerInit));
       memset(&PhyTimerTc, 0, sizeof(PhyTimerTc));
       memset(&RadTimerTc, 0, sizeof(RadTimerTc));
       
       memset(&ComLinkSetup, 0, sizeof(ComLinkSetup));
       memset(&SdLinkSetup, 0, sizeof(SdLinkSetup));
       memset(&RmLinkSetup, 0, sizeof(RmLinkSetup));
       memset(&TmLinkSetup, 0, sizeof(TmLinkSetup));
       memset(&PdLinkSetup, 0, sizeof(PdLinkSetup));
       memset(&PeLinkSetup, 0, sizeof(PeLinkSetup));
       memset(&RtLinkSetup, 0, sizeof(RtLinkSetup));
       memset(&AtLinkSetup, 0, sizeof(AtLinkSetup));
        
       // Initialize CSL library, this step is required 
       CSL_aif2Init(&Aif2Context);
       
       // Open Aif2 and get handle 
       hAif2 = CSL_aif2Open(&Aif2Obj, CSL_AIF, &aif2Param, &status);
    
       if ((hAif2 == NULL) || (status != CSL_SOK)) 
       {
          printf ("\nError opening CSL_AIF2");
          exit(1);
       }
       
       /************** populating AIF2 major setup structures ***************************************************/
       aif2Setup.globalSetup = &globalSetup;
       aif2Setup.commonSetup = &commonSetup;
       aif2Setup.linkSetup[CSL_AIF2_LINK_0] = &linkSetup;//assign only one link setup for link 0
     
       // populate global config fields
       globalSetup.ActiveLink[CSL_AIF2_LINK_0] = TRUE;//Activate link 0 for this test
       globalSetup.frameMode = CSL_AIF2_FRAME_MODE_NORMAL; 
      
       //populate common config fields
       commonSetup.pSdCommonSetup = &SdCommonSetup;
       commonSetup.pPdCommonSetup = &PdCommonSetup;
       commonSetup.pPeCommonSetup = &PeCommonSetup;
       commonSetup.pIngrDbSetup   = &IngrDbSetup;
       commonSetup.pEgrDbSetup    = &EgrDbSetup;
       commonSetup.pAdCommonSetup = &AdCommonSetup;
       commonSetup.pAtCommonSetup = &AtCommonSetup;
       commonSetup.pAtEventSetup  = &AtEventSetup; 
       
       /****Link Setup (Do this setup repeatedly with different link setup structure if user wants to use multiple links) ***/
       //populate link config fields for link 0
       linkSetup.linkIndex     = CSL_AIF2_LINK_0; 
       linkSetup.pComLinkSetup = &ComLinkSetup;
       linkSetup.pSdLinkSetup  = &SdLinkSetup;
       linkSetup.pRmLinkSetup  = &RmLinkSetup;
       linkSetup.pTmLinkSetup  = &TmLinkSetup;
       linkSetup.pPdLinkSetup  = &PdLinkSetup;
       linkSetup.pPeLinkSetup  = &PeLinkSetup;
       linkSetup.pRtLinkSetup  = &RtLinkSetup;
       linkSetup.pAtLinkSetup  = &AtLinkSetup;
       
       //Link Common setup
       ComLinkSetup.linkProtocol = CSL_AIF2_LINK_PROTOCOL_CPRI;
       ComLinkSetup.linkRate = CSL_AIF2_LINK_RATE_4x;
       ComLinkSetup.IngrDataWidth = CSL_AIF2_DATA_WIDTH_15_BIT;
       ComLinkSetup.EgrDataWidth = CSL_AIF2_DATA_WIDTH_15_BIT;
       
       //SD link setup
       SdLinkSetup.rxAlign = CSL_AIF2_SD_RX_COMMA_ALIGNMENT_ENABLE;
       SdLinkSetup.rxLos = CSL_AIF2_SD_RX_LOS_ENABLE;
       SdLinkSetup.rxCdrAlgorithm = CSL_AIF2_SD_RX_CDR_FIRST_ORDER_THRESH_17;
       SdLinkSetup.rxInvertPolarity = CSL_AIF2_SD_RX_NORMAL_POLARITY;
       SdLinkSetup.rxTermination = CSL_AIF2_SD_RX_TERM_COMMON_POINT_0_7 ;//for AC coupled application
       SdLinkSetup.rxEqualizerConfig = CSL_AIF2_SD_RX_EQ_ADAPTIVE;//Equalizer On
       SdLinkSetup.bRxEqHold = FALSE;//fixed value
       SdLinkSetup.bRxOffsetComp = TRUE;//fixed value
       SdLinkSetup.bEnableTxSyncMater = TRUE; //fixed value
       SdLinkSetup.txInvertPolarity = CSL_AIF2_SD_TX_PAIR_NORMAL_POLARITY;
       SdLinkSetup.txOutputSwing = CSL_AIF2_SD_TX_OUTPUT_SWING_14;
       SdLinkSetup.txPrecursorTapWeight = CSL_AIF2_SD_TX_PRE_TAP_WEIGHT_2;// -5%
       SdLinkSetup.txPostcursorTapWeight = CSL_AIF2_SD_TX_POST_TAP_WEIGHT_24;// -20%
       SdLinkSetup.bTxFirFilterUpdate = TRUE;//FIR filter update on
       
       //TM link setup
       TmLinkSetup.bEnableTmLink = TRUE;
       TmLinkSetup.bEnableRmLos = FALSE;
       TmLinkSetup.SeedValue = 0x1;
       TmLinkSetup.bEnableScrambler = FALSE;
       TmLinkSetup.pCpriTmSetup.L1InbandEn = 0;//disable 9 bits mask
       TmLinkSetup.pCpriTmSetup.RmLinkLosError = CSL_AIF2_LINK_0;//select link 0 as source RM link
       TmLinkSetup.pCpriTmSetup.RmLinkLofError = CSL_AIF2_LINK_0;//select link 0 as source RM link
       TmLinkSetup.pCpriTmSetup.RmLinkLosRx = CSL_AIF2_LINK_0;//select link 0 as source RM link
       TmLinkSetup.pCpriTmSetup.RmLinkLofRx = CSL_AIF2_LINK_0;//select link 0 as source RM link
       TmLinkSetup.pCpriTmSetup.RmLinkRaiRx = CSL_AIF2_LINK_0;//select link 0 as source RM link
       TmLinkSetup.pCpriTmSetup.TxStartup = 0;
       TmLinkSetup.pCpriTmSetup.TxPointerP = 20;
       TmLinkSetup.pCpriTmSetup.TxProtocolVer = 1;
       
       //RM link setup
       RmLinkSetup.bEnableRmLink = TRUE;
       RmLinkSetup.RmFifoThold = CSL_AIF2_RM_FIFO_THOLD_IMMEDIATELY;
       RmLinkSetup.RmErrorSuppress = CSL_AIF2_RM_ERROR_ALLOW;
       RmLinkSetup.bEnableSdAutoAlign = FALSE;
       RmLinkSetup.bEnableScrambler = FALSE;
       RmLinkSetup.bEnableLcvUnsync = FALSE;
       RmLinkSetup.bEnableLcvControl = FALSE;
       RmLinkSetup.bEnableWatchDog = FALSE;
       RmLinkSetup.WatchDogWrap = 0xFF;//set watch dog wrap value
       RmLinkSetup.bEnableClockQuality = FALSE;
       RmLinkSetup.ClockMonitorWrap = 0;
       RmLinkSetup.losDetThreshold = RM_LOS_DET_THOLD;
       RmLinkSetup.SyncThreshold = RM_SYNC_THOLD;
       RmLinkSetup.FrameSyncThreshold = RM_SYNC_THOLD;
       RmLinkSetup.UnsyncThreshold = RM_UNSYNC_THOLD;
       RmLinkSetup.FrameUnsyncThreshold = RM_UNSYNC_THOLD;
       
       //RT link setup
       RtLinkSetup.CiSelect =  CSL_AIF2_LINK_0;
       RtLinkSetup.bEnableEmptyMsg = TRUE;
       RtLinkSetup.RtConfig = CSL_AIF2_RT_MODE_TRANSMIT;// takes PE input only
       
       //PD link setup
       PdLinkSetup.bEnablePdLink = TRUE;
       PdLinkSetup.CpriEnetStrip = 0;//disable ethernet strip for control channel
       PdLinkSetup.Crc8Poly = CRC8_POLY;
       PdLinkSetup.Crc8Seed = CRC8_SEED;
       PdLinkSetup.CpriCwNullDelimitor = 0xFB;//K 27.7 charactor
       PdLinkSetup.CpriCwPktDelimitor[0] = CSL_AIF2_CW_DELIM_4B5B;
       PdLinkSetup.PdCpriCrcType[0] = CSL_AIF2_CRC_16BIT;
       PdLinkSetup.bEnableCpriCrc[0] = FALSE;//enable CPRI CRC for control channel 0
       PdLinkSetup.PdPackDmaCh[0] = 0;//Set DB channel 0 as a dma ch for control channel 0   
       PdLinkSetup.bEnablePack[0] = TRUE;//enable CPRI control channel 0 packing
       
       PdLinkSetup.PdCpriDualBitMap.DbmX = 0;// set X-1
       PdLinkSetup.PdCpriDualBitMap.DbmXBubble = 0;//2 bubbles of 1 AxC sample
       PdLinkSetup.PdCpriDualBitMap.Dbm1Mult = 0;//set n-1
       PdLinkSetup.PdCpriDualBitMap.Dbm1Size = 0;//set n-1
       PdLinkSetup.PdCpriDualBitMap.Dbm1Map[0] = 0x0;
       PdLinkSetup.PdCpriDualBitMap.Dbm2Size = 0;
       PdLinkSetup.PdCpriDualBitMap.Dbm2Map[0] = 0x0;
       PdLinkSetup.CpriDmaCh[0]= 0; //match DbmX channel 0 to DB channel 0 
       PdLinkSetup.bEnableCpriX[0]= TRUE; //enable CPRI X channel 0
       PdLinkSetup.bEnableCpriPkt[0]= TRUE;//use Pkt data for X channel 0
       PdLinkSetup.Cpri8WordOffset[0]= 0;//Word level CPRI data offset for X channel 0
       
       //PE link setup
       PeLinkSetup.bEnablePeLink = TRUE;
       PeLinkSetup.PeCppiDioSel = CSL_AIF2_CPPI;
       PeLinkSetup.TddAxc = FALSE;
       PeLinkSetup.PeDelay = DB_PE_DELAY_CPRI;//0 sys_clks delay between DB and PE
       PeLinkSetup.Crc8Poly = CRC8_POLY;
       PeLinkSetup.Crc8Seed = CRC8_SEED;
       PeLinkSetup.PeCpriDualBitMap.DbmX = 0;//set X-1
       PeLinkSetup.PeCpriDualBitMap.DbmXBubble = 0;//2 bubbles of 1 AxC sample
       PeLinkSetup.PeCpriDualBitMap.Dbm1Mult = 0;//set n-1
       PeLinkSetup.PeCpriDualBitMap.Dbm1Size = 0;//set n-1
       PeLinkSetup.PeCpriDualBitMap.Dbm1Map[0] = 0x0;
       PeLinkSetup.PeCpriDualBitMap.Dbm2Size = 0;
       PeLinkSetup.PeCpriDualBitMap.Dbm2Map[0] = 0x0;
       PeLinkSetup.CpriAxCPack = CSL_AIF2_CPRI_15BIT_SAMPLE;
       PeLinkSetup.CpriCwNullDelimitor = 0xFB;//K 27.7 character
       PeLinkSetup.CpriCwPktDelimitor[0] = CSL_AIF2_CW_DELIM_4B5B;
       PeLinkSetup.PePackDmaCh[0] = 0;//match DB channel 0 to control channel 0
       PeLinkSetup.bEnablePack[0] = TRUE;
       
       //AT link setup
       AtLinkSetup.PE1Offset = 300;
       AtLinkSetup.PE2Offset = 310;
       AtLinkSetup.DeltaOffset = 370;// Packet DMA delay + pe1 + pe2 = 300 + 10 + 60 (min Delta)
       AtLinkSetup.PiMin = 370;
       AtLinkSetup.PiMax = 390;
       AtLinkSetup.IsNegativeDelta = FALSE;//positive delta
       
       /************** Common Setup ********************************************************************************/
       //SD common setup
       SdCommonSetup.bEnablePllB8 = TRUE;
       SdCommonSetup.CLKBYP_B8 = CSL_AIF2_PLL_CLOCK_NO_BYPASS;
       SdCommonSetup.LB_B8 = CSL_AIF2_PLL_LOOP_BAND_MID;//High BW is also fine
       SdCommonSetup.VoltRangeB8 = CSL_AIF2_PLL_VOLTAGE_LOW;//fixed factor
       SdCommonSetup.SleepPllB8 = CSL_AIF2_PLL_AWAKE;
       SdCommonSetup.pllMpyFactorB8 = CSL_AIF2_PLL_MUL_FACTOR_20X;//for CPRI when reference clock is 122.88 Mhz
       SdCommonSetup.SysClockSelect = CSL_AIF2_SD_BYTECLOCK_FROM_B8;
       SdCommonSetup.DisableLinkClock[0] = FALSE;//enable link0 clock
       
       //PD common setup
       PdCommonSetup.PdCppiDioSel = CSL_AIF2_CPPI;//AxC data uses CPPI for DMA machine
       PdCommonSetup.PdChConfig[0].bChannelEn = TRUE;//Channel enable for channel 0
       PdCommonSetup.PdChConfig[0].DataFormat = CSL_AIF2_LINK_DATA_TYPE_NORMAL;//Data format for channel 0
       PdCommonSetup.PdChConfig1[0].DataFormat = CSL_AIF2_GSM_DATA_OTHER;//Non GSM data
       PdCommonSetup.PdChConfig1[0].TddEnable = 0xFFFF;//PD TDD, enables all symbols(FDD) for channel 0 
       PdCommonSetup.TddEnable1[0] = 0xFFFFFFFF;//enables all symbols(FDD)
       PdCommonSetup.TddEnable2[0] = 0xFFFFFFFF;//enables all symbols(FDD)
       PdCommonSetup.TddEnable3[0] = 0xFFFFFFFF;//enables all symbols(FDD)
       PdCommonSetup.TddEnable4[0] = 0xFFFFFFFF;//enables all symbols(FDD)
       
       //PE common setup
       PeCommonSetup.PeTokenPhase = 0;
       PeCommonSetup.EnetHeaderSelect = 0;//bit order for Ethernet preamble and SOF 
       
       PeCommonSetup.bEnableCh[0] = TRUE;//Enable PE channel for channel 0
       PeCommonSetup.PeDmaCh0[0].bCrcEn = FALSE;//disable CRC for channel 0
       PeCommonSetup.PeDmaCh0[0].RtControl = CSL_AIF2_PE_RT_INSERT;//use PE insert option for channel 0
       PeCommonSetup.PeDmaCh0[0].CrcType = CSL_AIF2_CRC_16BIT;//CRC type for channel 0
       PeCommonSetup.PeDmaCh0[0].isEthernet = FALSE;//AxC data 
       PeCommonSetup.PeDmaCh0[0].CrcObsaiHeader = FALSE;//calculate OBSAI header CRC
       PeCommonSetup.PeInFifo[0].SyncSymbol = 0;//sync symbol offset for channel 0
       PeCommonSetup.PeInFifo[0].MFifoWmark = 2;//Message FIFO water mark for channel 0
       PeCommonSetup.PeInFifo[0].MFifoFullLevel = 3;//Message FIFO full level for channel 0
       
       PeCommonSetup.ChIndex0[0] = 0; //channel 0
       PeCommonSetup.bEnableChIndex0[0] = TRUE;//Route egress channel 0 to CPRI link 0
       PeCommonSetup.CpriPktEn0[0] = TRUE; //use channel 0 for Pkt
       
       //Ingress DB setup
       IngrDbSetup.bEnableIngrDb = TRUE; //Enable Ingress DB
       IngrDbSetup.bEnableChannel[0] = TRUE; //Enable Ingress DB channel 0
       IngrDbSetup.IngrDbChannel[0].BaseAddress = AIF2_DB_BASE_ADDR_I_FIFO_0; //Set DB FIFO base address for channel 0
       IngrDbSetup.IngrDbChannel[0].BufDepth = CSL_AIF2_DB_FIFO_DEPTH_QW128; //Set DB FIFO depth for channel 0 
       IngrDbSetup.IngrDbChannel[0].DataSwap = CSL_AIF2_DB_WORD_SWAP; //DL
       IngrDbSetup.IngrDbChannel[0].IQOrder = CSL_AIF2_DB_IQ_NO_SWAP; //No Order change
       IngrDbSetup.IngrDbChannel[0].bEnablePsData = FALSE; //Enable 4 bytes PS data
       IngrDbSetup.IngrDbChannel[0].PacketType = 0; //User data
       
       //Egress DB setup
       EgrDbSetup.bEnableEgrDb = TRUE; //Enable Ingress DB
       EgrDbSetup.PmControl = CSL_AIF2_DB_AXC_TOKEN_FIFO;//to enhance CPRI packet performance
       EgrDbSetup.bEnableChannel[0] = TRUE; //Enable Egress DB channel 0
       EgrDbSetup.EgrDbChannel[0].BaseAddress = AIF2_DB_BASE_ADDR_E_FIFO_0; //Set DB FIFO base address for channel 0
       EgrDbSetup.EgrDbChannel[0].BufDepth = CSL_AIF2_DB_FIFO_DEPTH_QW128; //Set DB FIFO depth for channel 0
       EgrDbSetup.EgrDbChannel[0].DataSwap = CSL_AIF2_DB_WORD_SWAP; //DL
       EgrDbSetup.EgrDbChannel[0].IQOrder = CSL_AIF2_DB_IQ_NO_SWAP; //No Order change
       
       //AD Common setup
       AdCommonSetup.IngrGlobalEnable = TRUE;
       AdCommonSetup.EgrGlobalEnable = TRUE;
       AdCommonSetup.FailMode = CSL_AIF2_AD_DROP;//drop fail packet
       AdCommonSetup.IngrPriority = CSL_AIF2_AD_PKT_PRI;
       AdCommonSetup.EgrPriority = CSL_AIF2_AD_NON_AXC_PRI;
       AdCommonSetup.Tx_QueNum = AIF2_BASE_TX_QUE_NUM;//base egress queue number setup to 512
       
       //AT Common setup
       AtCommonSetup.PhySyncSel = CSL_AIF2_SW_SYNC;//Select SW sync for Phy timer trigger
       AtCommonSetup.RadSyncSel = CSL_AIF2_SW_SYNC;//Select SW sync for Rad timer trigger
       AtCommonSetup.SyncMode = CSL_AIF2_NON_RP1_MODE;
       AtCommonSetup.AutoResyncMode = CSL_AIF2_AUTO_RESYNC_MODE;
       AtCommonSetup.CrcMode = CSL_AIF2_AT_CRC_DONT_USE;//Do not use RP1 CRC in this test
       AtCommonSetup.PhytCompValue = 0;
       
       AtCommonSetup.AtInit.pPhyTimerInit = &PhyTimerInit;
       AtCommonSetup.AtInit.pRadTimerInit = &RadTimerInit;
       PhyTimerInit.ClockNum = 0;
       PhyTimerInit.FrameLsbNum = 0;
       PhyTimerInit.FrameMsbNum = 0;
       RadTimerInit.ClockNum = 0;
       RadTimerInit.SymbolNum = 0;
       RadTimerInit.FrameLsbNum = 0;
       RadTimerInit.FrameMsbNum = 0;
       AtCommonSetup.AtTerminalCount.pPhyTimerTc = &PhyTimerTc;
       AtCommonSetup.AtTerminalCount.pRadTimerTc = &RadTimerTc;
       PhyTimerTc.FrameLsbNum = FRAME_COUNT_TC_PHY_TIMER;//set phy Frame TC to 4095
       PhyTimerTc.ClockNum = CLOCK_COUNT_TC_PHY_TIMER_CPRI; //set phy clock TC for CPRI
       RadTimerTc.FrameLsbNum = FRAME_COUNT_TC_LTE_FDD;//set Frame TC to 4095
       RadTimerTc.SymbolNum = SYMBOL_COUNT_TC_LTE_FDD; //set Symbol TC to 9
       RadTimerTc.LutIndexNum = 0; //set LutIndex TC to 0
       AtCommonSetup.AtTerminalCount.RadClockCountTc[0] = CLOCK_COUNT_TC_LTE_FDD_CPRI;//set Clock count TC for CPRI
       
       //AT Event setup (Event 7)
       AtEventSetup.AtRadEvent[7].EventSelect = CSL_AIF2_EVENT_7;//Select Event 7 
       AtEventSetup.AtRadEvent[7].EventOffset = 1000; 
       AtEventSetup.AtRadEvent[7].EvtStrobeSel = CSL_AIF2_RADT_FRAME; 
       AtEventSetup.AtRadEvent[7].EventModulo = 2457599; 
       AtEventSetup.AtRadEvent[7].EventMaskLsb = 0xFFFFFFFF; 
       AtEventSetup.AtRadEvent[7].EventMaskMsb = 0xFFFFFFFF; 
       AtEventSetup.bEnableRadEvent[7] = TRUE;//Enable Event 7
       
       /****** Do AIF2 HW setup (set all MMRs above) **********************************************************************/
       CSL_aif2HwSetup(hAif2, &aif2Setup);
    
       ctrlArg = TRUE;
       hAif2->arg_link = CSL_AIF2_LINK_0;//Select link num
       
       //Enable Serdes loopback for link 0
       CSL_aif2HwControl(hAif2, CSL_AIF2_CMD_ENABLE_DISABLE_LINK_LOOPBACK, (void *)&ctrlArg);
       //Enable Tx/Rx of link 0
       CSL_aif2HwControl(hAif2, CSL_AIF2_CMD_ENABLE_DISABLE_TX_LINK, (void *)&ctrlArg);
       CSL_aif2HwControl(hAif2, CSL_AIF2_CMD_ENABLE_DISABLE_RX_LINK, (void *)&ctrlArg);
       for(i=0;i<100;i++)asm (" NOP 9 ");//insert time delay for aif2 configuration completion 
       
       //AT Arm timer
       CSL_aif2HwControl(hAif2, CSL_AIF2_CMD_AT_ARM_TIMER, (void *)&ctrlArg);
       
       //Trigger the SW debug frame sync
       CSL_aif2HwControl(hAif2, CSL_AIF2_CMD_AT_DEBUG_SYNC, (void *)&ctrlArg);
    
    }
    
    void Aif2_Halt_Timer(void)
    {
        ctrlArg = TRUE;
    	CSL_aif2HwControl(hAif2, CSL_AIF2_CMD_AT_DISABLE_ALL_EVENTS, (void *)&ctrlArg);
        CSL_aif2HwControl(hAif2, CSL_AIF2_CMD_AT_HALT_TIMER, (void *)&ctrlArg);
    }
    
    void Aif2_Close(void)
    {
       ctrlArg = FALSE;//disable AD scheduler and Rx, Tx Link
       CSL_aif2HwControl(hAif2, CSL_AIF2_CMD_AD_E_ENABLE_DISABLE_GLOBAL, (void *)&ctrlArg);
       CSL_aif2HwControl(hAif2, CSL_AIF2_CMD_AD_IN_ENABLE_DISABLE_GLOBAL, (void *)&ctrlArg);
       CSL_aif2HwControl(hAif2, CSL_AIF2_CMD_ENABLE_DISABLE_TX_LINK, (void *)&ctrlArg);
       CSL_aif2HwControl(hAif2, CSL_AIF2_CMD_ENABLE_DISABLE_RX_LINK, (void *)&ctrlArg);
       CSL_aif2Reset(hAif2);//reset all aif2 modules 
       CSL_aif2Close(hAif2);
    }
    
    void Test_result(void){
    	Uint32 i,result,destLen,base,index,count, test_pass = 1;
    	Cppi_Desc               *rxPkt;
    	Qmss_Queue              queInfo;
    	
        /* Read Entry count in accumulator */
        base = 0; //get data from only ping buffer
        count = hiPrioList[base];
        if(count == 0)test_pass = 0;
        hiPrioList[base] = 0;
        for (index = base + 1; index <= base + count; index++)
        {
            rxPkt = (Cppi_Desc *) QMSS_DESC_PTR (hiPrioList[index]);
            hiPrioList[index] = 0;
        
            /* Get data buffer */
            Cppi_getData (Cppi_DescType_HOST, rxPkt, &rxBuffPtr, &destLen);
            
            /* Compare */
            for (i = 0; i < destLen; i++)
            {
                if (tx_buffer[i] != rxBuffPtr[i])
                    test_pass = 0;
            }
                
            /* Recycle the Rx host descriptors */
            queInfo.qMgr = 0;
            queInfo.qNum = HOST_RX_FDQ;
            /* Push descriptor back to Rx free queue */
            Qmss_queuePushDesc (Qmss_getQueueHandle(queInfo), (Uint32 *) rxPkt);
        }
        
        if (test_pass == 1)
          printf(" Test a) Generic Packet Data Send/Recv: PASS\n");
        else
          printf(" Test a) Generic Packet Data Send/Recv: FAIL\n");
    
        result = Qmss_getQueueEntryCount (txQueHnd);
        if (result != 0) printf(" Test b1) Host Packet Tx Descriptor Counts:%d FAIL\n",result);
        else printf(" Test b1) Host Packet Tx Descriptor Counts:%d PASS\n",result);
        
        result = Qmss_getQueueEntryCount (txFreeQueHnd);
        if (result != 8) printf(" Test b2) Host Packet Tx Free Descriptor Counts:%d FAIL\n",result);
        else printf(" Test b2) Host Packet Tx Free Descriptor Counts:%d PASS\n",result);
        
        result = Qmss_getQueueEntryCount (freeQueHnd);
        if (result != 8) printf(" Test b3) Host Packet Rx Free Descriptor Counts:%d FAIL\n",result);
        else printf(" Test b3) Host Packet Rx Free Descriptor Counts:%d PASS\n",result);
    
        result = Qmss_getQueueEntryCount (rxQueHnd);
        if (result != 0) printf(" Test b4) Host Packet Rx Descriptor Counts:%d FAIL\n",result);
        else printf(" Test b4) Host Packet Rx Descriptor Counts:%d PASS\n",result);
        
        printf("Ending AIF2 CPRI GENERIC PACKET test\n");
    }
    
    void Intc_Close(void)
    { 
       CSL_intcHwControl(hIntc[0], CSL_INTC_CMD_EVTDISABLE, NULL);//Disable the Event & the interrupt 
       CSL_intcHwControl(hIntc[1], CSL_INTC_CMD_EVTDISABLE, NULL);//Disable the Event & the interrupt 
       CSL_intcGlobalDisable(&state);// Disable Global Interrupts  
       CSL_intcClose(hIntc[0]); // Close handles 
       CSL_intcClose(hIntc[1]); // Close handles 
    }
    
    void MNav_Close(void){
    	
    	/* Close Tx, Rx channel */
        Cppi_channelClose (txChHnd);
        Cppi_channelClose (rxChHnd);
        /* Close Rx flow */
        Cppi_closeRxFlow (rxFlowHnd);
           
        /* Close the queues */
        Qmss_queueClose (rxQueHnd);
        Qmss_queueClose (txQueHnd);
        Qmss_queueClose (freeQueHnd);
        Qmss_queueClose (txFreeQueHnd);
          
        /* Close AIF2 PKTDMA instance */
        Cppi_close (cppiHnd);
        /* Deinitialize Navigator LLD */
        Cppi_exit ();
    }
    
    void main(void)
    {
        printf("\nBeginning AIF2 CPRI GENERIC PACKET test:\n");
        
        enable_module(aif_pdctl, aif_mdctl);//Enable AIF2 module power
       
        Init_data_buffer();
        
        Intc_config();
        
        MNav_config();//Navigator and PKTDMA configuration
        
        Aif2_config();//Aif2 configuration for Cppi mode
    
         /*****************************************************************
        * Enable AIF and wait for completion.
        */
        while(1)
        {
            asm (" NOP 9 ");
    	    asm (" NOP 9 ");
            if(int5_result > 0)//Wait more than two frame time
            {
                //halt timer and close AIF2
                Aif2_Halt_Timer();
                Aif2_Close();
                break;
            }
        }
    
        Test_result(); //wait and compare src and dst data
    
        MNav_Close();
            
        Intc_Close();
    }