// +FHDR------------------------------------------------------------
//                 Copyright (c) 2022 SmartLogic.
//                       ALL RIGHTS RESERVED
// -----------------------------------------------------------------
// Filename      : ecs_rfm_spu0_oam.c
// Author        : huanfeng.wang
// Created On    : 2023-05-22
// Last Modified :
// -----------------------------------------------------------------
// Description:
// 
//
// -FHDR------------------------------------------------------------

#include "typedef.h"
#include "ucp_printf.h"
#include "ucp_utility.h"
#include "ucp_tick.h"
#include "msg_transfer_queue.h"
#include "pet_rfm_spu1_oam.h"
#include "app_interface.h"

#define RFM_OAM_MSG_SIZE   (8)
#define RFM_MSG_TYPE       (0)


static uint32_t g_u32_rfm0_oam_alloc_err = 0; //(31) 0xB7E0147C
static uint32_t g_u32_rfm0_oam_send_err  = 0; //(32) 0xB7E01480
static uint32_t g_u32_rfm0_oam_recv_num  = 0; //(33) 0xB7E01484
static uint32_t g_u32_rfm0_oam_send_ok   = 0; //(34) 0xB7E01488

uint32_t spu_rx_callback_oam(const char* buf,uint32_t payloadSize)
{
    /* RFM0接收OAM消息后发给RFM1 */
    uint32_t core_id = get_core_id();
    int32_t  ret = 0;
    char *addr = NULL;
    //uint32_t u32_clock_tick   = 0;

    UCP_PRINT_LOG("spu_rx_callback_oam,buf[0x%x] payloadSize[%d]", buf, payloadSize);

    //rdmcycle(&u32_clock_tick);
    //do_write((buf+16), u32_clock_tick); //RFM receive tick
    g_u32_rfm0_oam_recv_num++;

    addr = osp_alloc_msg(RFM_OAM_MSG_SIZE);
    if (NULL == addr)
    {    
        UCP_PRINT_ERROR("spu_rx_callback_oam,addr is nullpayloadSize[%d]", payloadSize);
        debug_write(DBG_DDR_COMMON_IDX(core_id, 31), ++g_u32_rfm0_oam_alloc_err);
        return payloadSize;
    }

    /* 第一字节：msg_transfer中的地址
       第二字节：bufer 的长度*/
    do_write(addr, (uint32_t)buf);
    do_write((addr+4), payloadSize);
    debug_write(DBG_DDR_COMMON_IDX(core_id, 43), buf);/*0xb7e014ac*/
    debug_write(DBG_DDR_COMMON_IDX(core_id, 44), payloadSize);
    debug_write(DBG_DDR_COMMON_IDX(core_id, 45), addr);

    //rdmcycle(&u32_clock_tick);
    //do_write((buf+20), u32_clock_tick); //RFM forward tick

    ret = osp_send_msg_oam((uint32_t)(addr), // osp_send_msg_oam
                        RFM_OAM_MSG_SIZE,
                        0xab,   /*SPU_OAM_MSG_TYPE*/
                        10,     /* src que id*/
                        11,     /* dst que id*/
                        40,     /* src task id*/
                        40);    /* dst task id*/
    if (0 != ret)
    {    
        UCP_PRINT_ERROR("spu_rx_callback_oam,ret[%d] nullpayloadSize[%d] g_u32_rfm0_oam_send_err[%d]", 
                          ret, payloadSize, g_u32_rfm0_oam_send_err);
        debug_write(DBG_DDR_COMMON_IDX(core_id, 32), ++g_u32_rfm0_oam_send_err);
        return payloadSize;
    }
    g_u32_rfm0_oam_send_ok++;

    debug_write(DBG_DDR_COMMON_IDX(core_id, 33), g_u32_rfm0_oam_recv_num);
    debug_write(DBG_DDR_COMMON_IDX(core_id, 34), g_u32_rfm0_oam_send_ok);

    UCP_PRINT_LOG("spu_rx_callback_oam,g_u32_rfm0_oam_recv_num[%d] g_u32_rfm0_oam_send_ok[%d] g_u32_rfm0_oam_send_err[%d]", 
                          g_u32_rfm0_oam_recv_num, g_u32_rfm0_oam_send_ok, g_u32_rfm0_oam_send_err);
    
    return payloadSize;
}

void spu_oam_init(void)
{
    uint16_t inst_id = 0;
    uint16_t transfer_type = 0;
    uint16_t cu_flag = C_PLANE;
    int32_t handle_id = 0;

    for (inst_id=0; inst_id<MAX_INSTANCE_NUM; inst_id++) {
        transfer_type = OAM;
        handle_id = msg_transfer_callback_register(transfer_type, inst_id,cu_flag, spu_rx_callback_oam);
        if (handle_id < 0) {
            UCP_PRINT_ERROR("spu_oam_init transfer_type:OAM, handle_id[0x%08x] error.",handle_id);
        }
    }

    return;
}





