/********************************************************
*                                                                                                            
* 文 件 名： ParsePackLeuData.c   
* 版权说明： 北京交控科技有限公司 
* 创建时间： 2012-03-28
* 作    者： 联锁组
* 功能描述： Leu数据解析头文件  
* 函数包括：
* 使用注意：
* 修改记录：   
*
********************************************************/ 



#include "ParsePackLeuData.h"



UINT8 LeuData[LEU_TO_CI_DATA_LEN_MAX] = {0u};         /*Leu数据*/
UINT16 LeuDataSum;          /*Leu数据长度*/
UINT8 leuToCiSum = 0u;/*与联锁通信的LEU数目*/
UINT8 leuFaultFlag = 1u;/*LEU故障标志，1无故障，0故障*/
LeuToCiDataStruct LeuToCiDataStru[LEU_TO_CI_SUM_MAX] = {0u};

/*
* 功能描述： 保存LEU数据
* 参数说明： const UINT8* dataBuf, 数据缓冲区
*            const UINT16 dataLength, 数据长度   
* 返回值  ： void       
*/
void SaveLeuToCiData(const UINT8* dataBuf, const UINT16 dataLength)
{
    UINT16 ii = 0u;

    if ((dataLength > 0u) && (dataBuf != NULL) && (dataLength + LeuDataSum < LEU_TO_CI_DATA_LEN_MAX))
    {/*参数有效&&未溢出*/
 
        for (ii = 0u; ii < dataLength; ii++)
        {
            LeuData[LeuDataSum] = dataBuf[ii];
            LeuDataSum = LeuDataSum + 1u;
        }    
    }
    else
    {
        /*存入LEU数据错误 数组清零*/
        LeuDataSum = 0u;
    }
}

/*
* 功能描述： 解析处理LEU单帧数据
* 参数说明： const UINT8* dataBuf, 数据缓冲区
*            const UINT16 dataLength, 数据长度
*            const UINT8 systemId, 源设备ID
* 返回值  ： 0: 数据解析失败
*			 1: 数据解析成功      
*/
UINT8 ParseLeuToCiDataFrame(const UINT8* dataBuf, const UINT16 dataLenth, const UINT8 systemId)
{
	UINT8 retVal = CI_ERROR;
	UINT8 ii = 0u;			/*索引*/
	UINT8 jj = 0u;
	UINT8 kk = 0U;
	UINT8 leuIndex = 0U;
	UINT8 leuNum = 0U;
	UINT8 localCiId = 0u; /*本方CI ID*/
	UINT32 curCycleNo = 0u; /*当前周期号*/

	leuNum = Get2oo2CiAndOtherSysCommNum(CI_SYSTEM_TYPE_LEU);		/*与CI通信LEU数量*/
	localCiId = GetSystemParaLocalCiId();
	curCycleNo = Get2oo2CurCycleNum();

	if (NULL == dataBuf)
	{
		;
	}
	else
	{
		if (leuNum < leuToCiSum)
		{
			debug_infor_printf((const)"LeuToCiSumError,leuNum= %d ,leuToCiSum=%d/n", leuNum, leuToCiSum);
		}
		else
		{
			ii++;	/*保留字节跳过*/
			retVal = CI_SUCCESS;
			for (kk = 0U; kk < leuToCiSum; kk++)
			{
				if (LeuToCiDataStru[kk].idInfo[2] == dataBuf[ii])
				{
					leuIndex = kk;
					break;
				}
				else
				{
					;/*未找到，继续找是否已经有LEU*/
				}
			}

			if (kk == leuToCiSum)
			{
				leuIndex = leuToCiSum;
				leuToCiSum++;		/*新LEU，数量增加*/
			}
			else
			{
				;/*已有LEU，覆盖既有的LEU状态*/
			}
			LeuToCiDataStru[leuIndex].idInfo[2] = dataBuf[ii];/*LEU ID，取低字节的每个CI的第几个LEU作为ID */

			ii += 3U;	/*LEU ID标示符3个字节中的低字节跳过CI+线路号*/
			LeuToCiDataStru[leuIndex].allState = dataBuf[ii++];/*LEU整机状态*/

			LeuToCiDataStru[leuIndex].leuType = dataBuf[ii++];/*LEU类型*/
			LeuToCiDataStru[leuIndex].toQianjiComState = dataBuf[ii++];/*与前级通信状态*/
			ii++;    /*跳过板级状态*/
			for (jj = 0u; jj < 4u; jj++)
			{/*LEU输出口1234状态，共4字节*/
				LeuToCiDataStru[leuIndex].outState[jj] = dataBuf[ii++];
			}
			for (jj = 0u; jj < 12u; jj++)
			{/*码位信息，12字节*/
				LeuToCiDataStru[leuIndex].maskInfo[jj] = dataBuf[ii++];
			}

			if (ii > dataLenth)
			{
				retVal = CI_ERROR;
			}
			else
			{

			}
		}
		
		if (CI_SUCCESS == retVal)
		{
			(void)SetCiTransmitRecvDataCycNum(localCiId, CI_SYSTEM_TYPE_LEU, systemId, curCycleNo);	/*收到LEU信息设置周期号，更新通信周期号*/
			LeuToCiDataStru[leuIndex].errorToAtsFlag = LEU_TO_ATS_ERRORFLAG_YES;			/*收到LEU数据，若有整机故障报警，可以向ATS报警*/
		}
	}
	return retVal;
}

/*
* 功能描述： 组LEU数据
* 参数说明： UINT8 deviceId, 目标设备ID    
* 返回值  ： 0:组数据失败
*			 1:组数据成功      
*/
UINT8 PackCiToLeuData(UINT8 deviceId)
{
    UINT8 localCi = GetSystemParaLocalCiId(); /*本地联锁ID*/
    UINT8 CiToLeuDataBuffer[CI_TO_LEU_DATA_LEN_MAX+5U] = {0u};/*CI到LEU组帧数组  CI_TO_LEU_DATA_LEN_MAX为应用数据定长要求*/
    UINT16 SendMaskSum = 0u;
    UINT16 ii = 0u;
	UINT16 row = 0u;
	UINT16 kk = 0u;
	UINT16 index = 0u;			/*字节索引*/
	UINT16 maskid = 0u;			/*复示码位ID*/
	UINT8 currentValue = 0u;		/*当前码位数据*/
	UINT16 divNum = 0u;			/*除数*/
	UINT16 remNum = 0u;			/*余数*/
	UINT16 dstDevId = 0u;
	UINT8 outnetSafeSendRtn = 0u;
        
    /*获取将要发送的码位字节数*/
    if (GetSendMaskSum(CI_SYSTEM_TYPE_LEU) % 8u == 0u)
    {
        SendMaskSum = (UINT16) (GetSendMaskSum(CI_SYSTEM_TYPE_LEU) / 8u);
    }
    else
    {
        SendMaskSum = (UINT16) (GetSendMaskSum(CI_SYSTEM_TYPE_LEU) / 8u + 1u);
    }
        
    if ((SendMaskSum == 0u) || (SendMaskSum > CI_TO_LEU_DATA_LEN_MAX/2u))
    {/*无应用数据或数据超出则返回*/
        return CI_ERROR;
    }

    /*组码位信息*/
	(void)MaskPack(CI_SYSTEM_TYPE_LEU,&CiToLeuDataBuffer[ii]);
    ii = (UINT16) (ii + SendMaskSum);
		
	/*补齐复示码位*/
    for (row = (UINT16) (ii - SendMaskSum); row < ii; row++)
    {
        currentValue = CiToLeuDataBuffer[row];
        for (kk = 0u; kk < 8u; kk++)
        {
			maskid = index * 8u + GetSendMaskSum(CI_SYSTEM_TYPE_LEU) + kk + 1u;/*复示码位ID*/
			if ((maskid > GetSendMaskSum(CI_SYSTEM_TYPE_LEU)) && (maskid <= GetSendMaskSum(CI_SYSTEM_TYPE_LEU) * 2u))
			{
				/*删除 5偏移量*/
				divNum = (UINT16) ((maskid / 8u));
				remNum = (UINT16) (maskid % 8u);

					if (((currentValue >> (7u - kk)) & 0x01u) == 0x01u)
					{
						/*置1*/
						if (0u == remNum)
						{
							CiToLeuDataBuffer[divNum - 1U] = (UINT8)(CiToLeuDataBuffer[divNum - 1U] | 0x01u);/*divNum只在0-7中取值*/
						}
						else
						{
								CiToLeuDataBuffer[divNum] = (UINT8)(CiToLeuDataBuffer[divNum] | (0x80u >> (remNum - 1U)));
					}
					
			    	}
				    else
				    {
				    }
			} 
			else
			{
				continue;
			}
        }
		index++;
    }

    ii = CI_TO_LEU_DATA_LEN_MAX;

	dstDevId = ((UINT16)(CI_SYSTEM_TYPE_LEU << 8) | ((UINT16)deviceId));
	outnetSafeSendRtn = OutnetSafeSend(dstDevId, 0u, &CiToLeuDataBuffer[0], ii);
	if (1u == outnetSafeSendRtn)
    { /*写队列成功*/
#ifdef LOGPRINT/*日志打印宏*/            
#ifdef PLATFORM_2OO2/*2oo2平台打印*/
        debug_infor_printf((const)"\nLEU_SEND:%d", ii);
        debug_out_array(0xAA, CiToLeuDataBuffer, ii);
#endif/*平台打印结束*/
#endif
        return CI_SUCCESS;
    }
    else
    {
        return CI_ERROR;
    }
    
    
}

/*
* 功能描述： 清除LEU数据
* 参数说明： void    
* 返回值  ： void       
*/
void ClearLeuToCiData(void)
{
    UINT16 ii = 0u;

    for (ii = 0u; ii < LeuDataSum; ii++)
    {
        LeuData[ii] = 0u;
    }
    LeuDataSum = 0u;
}

/*
* 功能描述： 获取LEU数据长度
* 参数说明： void    
* 返回值  ： 数据长度       
*/
UINT16 GetLeuDataLen(void)
{
    return LeuDataSum;
}

/*
* 功能描述： 获取LEU数据
* 参数说明： void    
* 返回值  ： 数据     
*/
UINT8* GetLeuData(void)
{
    return LeuData;
}

/*
* 功能描述： 获取与CI通信的LEU数目
* 参数说明： void    
* 返回值  ： 与CI通信的LEU数目       
*/
UINT16 GetLeuToCiSum(void)
{
	return leuToCiSum;
}

/*
* 功能描述： 获取LEU与CI通信数据结构体
* 参数说明： void    
* 返回值  ： LEU与CI通信数据结构体指针       
*/
LeuToCiDataStruct* GetLeuToCiDataStru(void)
{
	return LeuToCiDataStru;
}

/*
* 功能描述： 清除所有通信的LEU的报警标志
* 参数说明： void
* 返回值  ： 无
*/
void ClearAllErrorFlag(void)
{
	UINT16 leuSum = GetLeuToCiSum();/*与CI通信的LEU数目*/
	UINT16 ii = 0U;

	for (ii = 0U; ii < leuSum; ii++)
	{
		LeuToCiDataStru[ii].errorToAtsFlag = LEU_TO_ATS_ERRORFLAG_NO;
	}
}