/**********************************************************************************************************************
*  Copyright (C), 2022-2026, SMARTLOGIC TECHNOLOGY LTD.
*  File Name: ecpri_test_case117.s.c
*  Create Date: 24/01/17
*  Description: eCPRI Test Case117 Module Source File
*  Change History: 
*      <author>      <time>      <version>   <desc>
*    1. ShangH      24/01/17        1.0       Build this module
**********************************************************************************************************************/


/* -------------------------------------------------- <INC FILE> --------------------------------------------------- */
#include "ecpri_test_case117.h"


/* --------------------------------------------------- <VAR DEF> --------------------------------------------------- */
#ifdef ECS_RFM0
/* eCPRI test ECS_RFM0 flag */
uint32_t g_ecpri_test_flag0 = 0; /* ECS_RFM0: 0xB7E32000(0) */
/* eCPRI test number */
uint32_t g_ecpri_test_num = 1; /* ECS_RFM0: 0xB7E32004(1) */

/* eCPRI test ECS_RFM0 result */
EcpriTestResult_t g_ecpri_test_result0 = {0}; /* ECS_RFM0: 0xB7E32010(4) ~ 0xB7E32018(6) */

/* eCPRI test send time statistic */
EcpriTimeStats_t g_ecpri_test_send_time_stats = {0, 0, 0xFFFFFFFF}; /* ECS_RFM0: 0xB7E32020(8) ~ 0xB7E32028(10) */

/* eCPRI CSU node parameter */
stEcpriCsuNodePara g_ecpri_csu_list_node[ECPRI_25G_ANT_NUM] = {0};
#endif

#ifdef ECS_RFM1
/* eCPRI test ECS_RFM1 flag */
uint32_t g_ecpri_test_flag1 = 0; /* ECS_RFM1: 0xB7E42000(0) */

/* eCPRI test ECS_RFM1 result */
EcpriTestResult_t g_ecpri_test_result1 = {0}; /* ECS_RFM1: 0xB7E42010(4) ~ 0xB7E42018(6) */
#endif


/* -------------------------------------------------- <FUNC DEF> --------------------------------------------------- */
/**********************************************************************************************************************
*  Function: fh_data_init
*  Description: fronthaul data init
*  Input: none
*  Output: none
*  Return: operation result - success or failure.
*  Others: none
**********************************************************************************************************************/
int32_t fh_data_init(void)
{
#ifdef ECS_RFM0
    ecpri_test_ecs0_init();
#endif

#ifdef ECS_RFM1
    ecpri_test_ecs1_init();
#endif

    return SUCCESS;
}

/**********************************************************************************************************************
*  Function: fh_drv_init
*  Description: fronthaul driver init
*  Input: none
*  Output: none
*  Return: operation result - success or failure.
*  Others: none
**********************************************************************************************************************/
int32_t fh_drv_init(void)
{
#ifdef ECS_RFM1
    /* eCPRI init */
    ecpri_init(ECPRI_OPTION_25G);
#endif

    return SUCCESS;
}

/**********************************************************************************************************************
*  Function: fh_csu_test_init
*  Description: fronthaul CSU test init
*  Input: none
*  Output: none
*  Return: operation result - success or failure.
*  Others: none
**********************************************************************************************************************/
int32_t fh_csu_test_init(void)
{
    return SUCCESS;
}

/**********************************************************************************************************************
*  Function: fh_data_check
*  Description: fronthaul data check
*  Input: 
*    <name>                    <type>                      <desc>
*     times                     uint32_t                    check times
*  Output: none
*  Return: none
*  Others: none
**********************************************************************************************************************/
void fh_data_check(uint32_t times)
{
#ifdef ECS_RFM0
    ecpri_test_ecs0_status_check();
#endif

#ifdef ECS_RFM1
    ecpri_test_ecs1_status_check();
#endif
}

/**********************************************************************************************************************
*  Function: fh_test_case
*  Description: fronthaul test case
*  Input: none
*  Output: none
*  Return: none
*  Others: none
**********************************************************************************************************************/
void fh_test_case(void)
{
    return;
}

#ifdef ECS_RFM0
/**********************************************************************************************************************
*  Function: ecpri_test_ecs0_init
*  Description: eCPRI test ECS_RFM0 init
*  Input: none
*  Output: none
*  Return: none
*  Others: none
**********************************************************************************************************************/
void ecpri_test_ecs0_init(void)
{
    /* antenna index */
    uint8_t ant_id = 0;
    /* config index */
    uint32_t cfg_id = 0;
    /* data address & length */
    uint32_t data_addr = 0;
    uint32_t data_len = 0;

    memset_ucp((void *)&g_ecpri_test_result0, 0, sizeof(g_ecpri_test_result0));

    memset_ucp((void *)g_ecpri_csu_list_node, 0, sizeof(g_ecpri_csu_list_node));

    /* send flag init(symbol interrupt) */
    debug_write(ECPRI_DBG_IDX0(64), 0); /* ECS_RFM0: 0xB7E30100(64) */
    /* send length init */
    debug_write(ECPRI_DBG_IDX0(65), 0); /* ECS_RFM0: 0xB7E30104(65) */
    /* send wait flag init */
    debug_write(ECPRI_DBG_IDX0(66), 0); /* ECS_RFM0: 0xB7E30108(66) */

    /* eCPRI symbol interrupt interval check flag init */
    debug_write(ECPRI_DBG_IDX0(68), 0); /* ECS_RFM0: 0xB7E30110(68) */
    /* eCPRI symbol interrupt status check flag init */
    debug_write(ECPRI_DBG_IDX0(69), 0); /* ECS_RFM0: 0xB7E30114(69) */
    /* eCPRI symbol interrupt parameter check flag init */
    debug_write(ECPRI_DBG_IDX0(70), 0); /* ECS_RFM0: 0xB7E30118(70) */

    /* test flag init */
    debug_write(ECPRI_TEST_IDX0(0), g_ecpri_test_flag0); /* ECS_RFM0: 0xB7E32000(0) */
    /* test number init */
    debug_write(ECPRI_TEST_IDX0(1), g_ecpri_test_num); /* ECS_RFM0: 0xB7E32004(1) */

    for (ant_id = 0; ant_id < ECPRI_25G_ANT_NUM; ant_id++)
    {
        /* config index */
        cfg_id = ant_id * ECPRI_SLOT_TYPE * ECPRI_SYM_NUM;

        /* data address & length */
        data_addr = do_read_volatile((void *)(ECPRI_ANT_BUF_ADDR + cfg_id * ECPRI_SYM_INFO_LEN));
        data_len = do_read_volatile((void *)(ECPRI_ANT_BUF_ADDR + cfg_id * ECPRI_SYM_INFO_LEN + sizeof(uint32_t)));

        g_ecpri_csu_list_node[ant_id].dataAddr = data_addr;
        g_ecpri_csu_list_node[ant_id].allNum = data_len;
    }

    g_ecpri_csu_list_node_ptr = g_ecpri_csu_list_node;

    /* eCPRI CSU link list init */
    ecpri_csu_tx_list_init(g_ecpri_csu_list_addr, ECPRI_25G_ANT_NUM, g_ecpri_csu_list_node_ptr);
}

/**********************************************************************************************************************
*  Function: ecpri_test_pl_pkt_proc
*  Description: eCPRI test PL packet process
*  Input: 
*    <name>                    <type>                      <desc>
*     pkt_addr                  uint32_t                    packet address
*     pkt_len                   uint16_t                    packet length
*  Output: none
*  Return: none
*  Others: none
**********************************************************************************************************************/
void ecpri_test_pl_pkt_proc(uint32_t pkt_addr, uint16_t pkt_len)
{
    return;
}

/**********************************************************************************************************************
*  Function: ecpri_test_ecs0_status_check
*  Description: eCPRI test ECS_RFM0 status check
*  Input: none
*  Output: none
*  Return: none
*  Others: none
**********************************************************************************************************************/
void ecpri_test_ecs0_status_check(void)
{
    /* return value */
    int32_t ret = 0;
    /* count index */
    uint32_t i = 0;
    /* wait flag */
    uint8_t wait_flag = 0;
    /* start & end cycle */
    uint32_t start_cycle = 0;
    uint32_t end_cycle = 0;

    /* get test flag */
    g_ecpri_test_flag0 = do_read_volatile((void *)ECPRI_TEST_ADDR0(0)); /* ECS_RFM0: 0xB7E32000(0) */
    if (0 == g_ecpri_test_flag0)
    {
        return;
    }

    /* get test number */
    g_ecpri_test_num = do_read_volatile((void *)ECPRI_TEST_ADDR0(1)); /* ECS_RFM0: 0xB7E32004(1) */

    /* get send wait flag */
    wait_flag = do_read_volatile((void *)ECPRI_DBG_ADDR0(66)); /* ECS_RFM0: 0xB7E30108(66) */
    if (0 != wait_flag)
    {
        wait_flag = 1;
    }

    for (i = 0; i < g_ecpri_test_num; i++)
    {
        g_ecpri_test_result0.test_times++;

        /* time start */
        rdmcycle(&start_cycle);

        /* eCPRI CSU link list send */
        ret = ecpri_csu_link_send(g_ecpri_csu_list_addr, ECPRI_25G_ANT_NUM, g_ecpri_csu_list_node, wait_flag);

        /* time end */
        rdmcycle(&end_cycle);

        g_ecpri_test_send_time_stats.time_cur = (end_cycle + STC_CYCLE_MAX - start_cycle) % STC_CYCLE_MAX + 1;
        debug_write(ECPRI_TEST_IDX0(8), g_ecpri_test_send_time_stats.time_cur); /* ECS_RFM0: 0xB7E32020(8) */

        if (g_ecpri_test_send_time_stats.time_max < g_ecpri_test_send_time_stats.time_cur)
        {
            g_ecpri_test_send_time_stats.time_max = g_ecpri_test_send_time_stats.time_cur;
            debug_write(ECPRI_TEST_IDX0(9), g_ecpri_test_send_time_stats.time_max); /* ECS_RFM0: 0xB7E32024(9) */
        }

        if (g_ecpri_test_send_time_stats.time_min > g_ecpri_test_send_time_stats.time_cur)
        {
            g_ecpri_test_send_time_stats.time_min = g_ecpri_test_send_time_stats.time_cur;
            debug_write(ECPRI_TEST_IDX0(10), g_ecpri_test_send_time_stats.time_min); /* ECS_RFM0: 0xB7E32028(10) */
        }

        if (ERROR != ret)
        {
            g_ecpri_test_result0.succ_times++;
        }
        else
        {
            g_ecpri_test_result0.fail_times++;
        }
    }

    /* eCPRI test ECS_RFM0 result update */
    ecpri_test_ecs0_result_update();

    /* clear ECS_RFM0 test flag */
    g_ecpri_test_flag0 = 0;
    debug_write(ECPRI_TEST_IDX0(0), g_ecpri_test_flag0); /* ECS_RFM0: 0xB7E32000(0) */
}

/**********************************************************************************************************************
*  Function: ecpri_test_ecs0_result_update
*  Description: eCPRI test ECS_RFM0 result update
*  Input: none
*  Output: none
*  Return: none
*  Others: none
**********************************************************************************************************************/
void ecpri_test_ecs0_result_update(void)
{
    debug_write(ECPRI_TEST_IDX0(4), g_ecpri_test_result0.test_times); /* ECS_RFM0: 0xB7E32010(4) */
    debug_write(ECPRI_TEST_IDX0(5), g_ecpri_test_result0.succ_times); /* ECS_RFM0: 0xB7E32014(5) */
    debug_write(ECPRI_TEST_IDX0(6), g_ecpri_test_result0.fail_times); /* ECS_RFM0: 0xB7E32018(6) */
}
#endif

#ifdef ECS_RFM1
/**********************************************************************************************************************
*  Function: ecpri_test_ecs1_init
*  Description: eCPRI test ECS_RFM1 init
*  Input: none
*  Output: none
*  Return: none
*  Others: none
**********************************************************************************************************************/
void ecpri_test_ecs1_init(void)
{
    /* antenna index */
    uint8_t ant_id = 0;
    /* slot type */
    uint8_t slot_type = 0;
    /* symbol index */
    uint8_t sym_id = 0;
    /* count index */
    uint16_t i = 0;

    /* eCPRI buffer clear */
    memset_ucp((void *)ECPRI_BUF_ADDR, 0x00, ECPRI_BUF_SIZE);

    /* data conversion */
    for (ant_id = 0; ant_id < ECPRI_25G_ANT_NUM; ant_id++)
    {
        HTON_L(g_tdd_ecpri_ant_cfg_data[ant_id].tdd_symx.tdd_ecpri_head.vlan_tag);
        HTON_S(g_tdd_ecpri_ant_cfg_data[ant_id].tdd_symx.tdd_ecpri_head.ether_type);
        HTON_S(g_tdd_ecpri_ant_cfg_data[ant_id].tdd_symx.tdd_ecpri_head.payload_size);

        for (i = 0; i < TDD_ECPRI_SYMX_COMP_LEN; i++)
        {
            HTON_L(g_tdd_ecpri_ant_cfg_data[ant_id].tdd_symx.tdd_symx_data[i]);
        }
    }

#if 1 /* DDR */
    /* eCPRI antenna config */
    for (ant_id = 0; ant_id < ECPRI_25G_ANT_NUM; ant_id++)
    {
        for (slot_type = 0; slot_type < ECPRI_SLOT_TYPE; slot_type++)
        {
            for (sym_id = 0; sym_id < ECPRI_SYM_NUM; sym_id++)
            {
                ecpri_ant_cfg(ant_id, slot_type, sym_id, 
                              (uint32_t)(&g_tdd_ecpri_ant_cfg_data[ant_id].tdd_symx), TDD_ECPRI_SYMX_PKT_LEN);
            }
        }
    }
#else /* SM */
    /* copy data from DDR to SM */
    memcpy_ucp((void *)ECPRI_TEST_SM_ADDR, 
               (void *)g_tdd_ecpri_ant_cfg_data, 
               sizeof(g_tdd_ecpri_ant_cfg_data));

    /* eCPRI antenna config */
    for (ant_id = 0; ant_id < ECPRI_25G_ANT_NUM; ant_id++)
    {
        for (slot_type = 0; slot_type < ECPRI_SLOT_TYPE; slot_type++)
        {
            for (sym_id = 0; sym_id < ECPRI_SYM_NUM; sym_id++)
            {
                ecpri_ant_cfg(ant_id, slot_type, sym_id, 
                              (uint32_t)(ECPRI_TEST_SM_ADDR + ant_id * TDD_ECPRI_SYMX_PKT_LEN), TDD_ECPRI_SYMX_PKT_LEN);
            }
        }
    }
#endif

    memset_ucp((void *)&g_ecpri_test_result1, 0, sizeof(g_ecpri_test_result1));

    /* ECS_RFM1 test flag init */
    debug_write(ECPRI_TEST_IDX1(0), g_ecpri_test_flag1); /* ECS_RFM1: 0xB7E42000(0) */
}

/**********************************************************************************************************************
*  Function: ecpri_test_ecs1_status_check
*  Description: eCPRI test ECS_RFM1 status check
*  Input: none
*  Output: none
*  Return: none
*  Others: none
**********************************************************************************************************************/
void ecpri_test_ecs1_status_check(void)
{
    /* get ECS_RFM1 test flag */
    g_ecpri_test_flag1 = do_read_volatile((void *)ECPRI_TEST_ADDR1(0)); /* ECS_RFM1: 0xB7E42000(0) */
    if (0 == g_ecpri_test_flag1)
    {
        return;
    }

    /* eCPRI test ECS_RFM1 result update */
    ecpri_test_ecs1_result_update();

    /* clear ECS_RFM1 test flag */
    g_ecpri_test_flag1 = 0;
    debug_write(ECPRI_TEST_IDX1(0), g_ecpri_test_flag1); /* ECS_RFM1: 0xB7E42000(0) */
}

/**********************************************************************************************************************
*  Function: ecpri_test_ecs1_result_update
*  Description: eCPRI test ECS_RFM1 result update
*  Input: none
*  Output: none
*  Return: none
*  Others: none
**********************************************************************************************************************/
void ecpri_test_ecs1_result_update(void)
{
    debug_write(ECPRI_TEST_IDX1(4), g_ecpri_test_result1.test_times); /* ECS_RFM1: 0xB7E42010(4) */
    debug_write(ECPRI_TEST_IDX1(5), g_ecpri_test_result1.succ_times); /* ECS_RFM1: 0xB7E42014(5) */
    debug_write(ECPRI_TEST_IDX1(6), g_ecpri_test_result1.fail_times); /* ECS_RFM1: 0xB7E42018(6) */
}
#endif



