#include "sys_config.h"

#if PRODUCT_SHTCP
#include "sys_processor.h"
#include "UWater_eeprom_driver.h"
#include "UWater_timer1us_driver.h"
#include "UWater_rtcc_app.h"
#include "UWater_power_app.h"
#include "UWater_gp22_app.h"
#include "UWater_pt_app.h" 
#include "UWater_valve_app.h"
#include "UWater_DataTools_App.h"
#include "UWater_QZ_Store_App.h"
#include "UWater_frame_func_ReplyNB.h"
#include "UWater_frame_func_ReplyShangHe.h"


static u8 task_complete_sh = PTL_PACK_FAIL;
static STRUCT_FRAME_SH s_frame_struct_SH; //规约信息 
static u8 up_deal_stat_sh  = UP_DEAL_S0;

static u16 g_frame_temp_len_sh=0;
static u8 g_frame_temp_send_buf_sh[UP_DATA_BUF_SIZE_SH];	//数据部分缓冲区
/*******主动上传数据相关变量*****************************************/
static STRU_TCP_UPLOAD_FRAME  tcp_upload_frame; 
static u8 upload_frame_stat_sh=0; //主动上报组帧状态
static u8 upload_task_complete_sh = PTL_PACK_FAIL;  
static u8* new_message_data_rev_sh;
static u8 temp_upload_step=0;
static u8 upload_frame_retry_times=0;
//控阀
static void frame_func_reply_TCP_ValveControl(void)
{
	g_frame_temp_len_sh = 0;
	if(*(new_message_data_rev_sh) == 0x55)//开阀
	{
		FrameSetMsgApp(ValveOpenMsg);
	}
	else if(*(new_message_data_rev_sh) == 0x99)//关阀
	{
		FrameSetMsgApp(ValveCloseMsg);
	}
	up_deal_stat_sh = up_deal_stat_sh;
	task_complete_sh = PTL_PACK_SUCCESS;     
}
static void frame_func_reply_TCP_AckUpload(void)
{
	g_frame_temp_len_sh = 0;
	if(*(new_message_data_rev_sh) == 0x01)//立即下线
	{
		FrameSetMsgApp(MsgNbUpload_OffLine);//立即下线
	}
	FrameSetMsgApp(MsgNbUplaod_AckOk);
	task_complete_sh = PTL_PACK_FAIL;
}

//解商河水务规约
u8 crack_frame_SHTCP(u16 frame_lenth,u8 *frame_buffer)
{
     u16 tmp_i = 0;
     u16 tmp_j = 0;
     u8 tmp_check = 0;
    for (tmp_i = 0; tmp_i < frame_lenth; tmp_i++)
    {
        if (FM_HEAD_MARK == *(frame_buffer + tmp_i))
        {
			if ((MET_TYPE_TCP == *(frame_buffer + tmp_i + 1))&&(UP_SOURCE_NB == frame_get_datasource()))
			{
				s_frame_struct_SH.met_type = MET_TYPE_TCP;
				s_frame_struct_SH.head_site = tmp_i; //记录帧头
				s_frame_struct_SH.len = *(frame_buffer + tmp_i + 10);//数据长度
				s_frame_struct_SH.end_site = s_frame_struct_SH.head_site + 10 + s_frame_struct_SH.len + 2;
				s_frame_struct_SH.check_len = s_frame_struct_SH.end_site - s_frame_struct_SH.head_site - 1;
				 if(FM_END_MARK == *(frame_buffer + s_frame_struct_SH.end_site))
				 {
					//计算校验和
					 tmp_check = 0;
					for (tmp_j = s_frame_struct_SH.head_site; tmp_j < (s_frame_struct_SH.end_site - 1); tmp_j++)
					{
						tmp_check += *(frame_buffer + tmp_j);
					}
					if (tmp_check == *(frame_buffer + s_frame_struct_SH.end_site - 1))
					{
						u8 check_addr[7];
						for (tmp_j = 0; tmp_j < 7; tmp_j++)
						{
							check_addr[tmp_j] = Sys_data_object.P1.met_addr[tmp_j];
						}
						s_frame_struct_SH.ctrl = *(frame_buffer + s_frame_struct_SH.head_site + 9);
						s_frame_struct_SH.DI0 = *(frame_buffer + s_frame_struct_SH.head_site + 11);
						s_frame_struct_SH.DI1 = *(frame_buffer + s_frame_struct_SH.head_site + 12);
						s_frame_struct_SH.serial_num0 = *(frame_buffer + s_frame_struct_SH.head_site + 13);
						new_message_data_rev_sh = (frame_buffer + s_frame_struct_SH.head_site + 14);
						switch(s_frame_struct_SH.ctrl)
						{
							case VALVE_CONTROL_TCP_CTRL:
							{
								check_addr[0] = check_addr[0]-1;//地址为设备地址码减一，最后一位为 0～8
							}
							break;
							default:
							{
							}
							break;
						}
						if(SUCCESS == check_apply_addr(frame_buffer + s_frame_struct_SH.head_site + 2, check_addr))
						{
							return  SUCCESS_IES;	
						}
					}
				 }
			}
        }
    }
    return ERROR_IES;
}

//规约处理
u8 up_deal_code_sh(void)
{
    task_complete_sh = PTL_PACK_BUSY;
    switch(s_frame_struct_SH.ctrl)
    {
		case VALVE_CONTROL_TCP_CTRL:
		{
			frame_func_reply_TCP_ValveControl();
			s_frame_struct_SH.ack_ctrl = ACK_VALVE_CONTROL_TCP_CTRL;
		}
		break;
		case FM_TCP_UPLOAD_REPLAY_CTRL:
		{
			frame_func_reply_TCP_AckUpload();
			s_frame_struct_SH.ack_ctrl = FM_TCP_UPLOAD_CTRL;
		}
		break;
        default:
        {     
			up_deal_stat_sh  = UP_DEAL_S0;
			task_complete_sh = PTL_PACK_FAIL;           
        }
        break;
    }
    return task_complete_sh;
}

void Frame_ResetDealState_SH(void)
{
	up_deal_stat_sh = UP_DEAL_S0;
}


void Frame_CreatCs_AckSH(u8* p_send_buf, u16* p_send_len)
{
    int i=0;
	//组应答帧头
	p_send_buf[0] = 0xFE;
    p_send_buf[1] = 0xFE;
    p_send_buf[2] = FM_HEAD_MARK;
    p_send_buf[3] = MET_TYPE;
	for (i = 0; i < 7; i++)
	{
		p_send_buf[4 + i] = Sys_data_object.P1.mac_addr[i];
	}
	p_send_buf[11] = s_frame_struct_SH.ack_ctrl;
	p_send_buf[12] = (3+g_frame_temp_len_sh);
	p_send_buf[13] = s_frame_struct_SH.DI0;
	p_send_buf[14] = s_frame_struct_SH.DI1;
	p_send_buf[15] = s_frame_struct_SH.serial_num0;
    for(i=0;i<g_frame_temp_len_sh;i++)
    {
       p_send_buf[16+i] = g_frame_temp_send_buf_sh[i];       
    }
	p_send_buf[16+g_frame_temp_len_sh] = check_cs(&p_send_buf[2], (p_send_buf[12] + 11));
	p_send_buf[17+g_frame_temp_len_sh] = FM_END_MARK;
	*p_send_len = (18+g_frame_temp_len_sh);
}

/****************************************************************以下主动上报数据的处理*********************************************/
static void Register_TcpFrameData(u8 *p_send_buf, u16 *p_send_len)
{
	u8 i=0;
	char imei_buf[16];
	
	NbiotGetIMEI(imei_buf); 

	for(i=0;i<15;i++)
	{
		*p_send_buf++ = imei_buf[i];
	}
	*p_send_len = 15;
}
static void Ping_TcpFrameData(u8 *p_send_buf, u16 *p_send_len)
{
	u8 i=0;

	for(i=0;i<3;i++)
	{
		*p_send_buf++ = '0';
	}
	*p_send_len = 3;
}
//TCP上报数据帧
static void Upload_TcpFrameData(u8* p_send_buf, u16* p_send_len)
{
	u8 i=0;
	UNION_4U8TOU32 tmp_datas_buf;
	u8 temp_data=0;
	TCP_STATE tcp_stat;
	MET_STATE temp_state;
	Fram_To_Float tmp_float;
	DateTime tempRtccTime;
	UNION_2U8TOU16 temp_bat_val;
	
	tcp_upload_frame.data.HeadBuf[0] = 0xFE;
	tcp_upload_frame.data.HeadBuf[1] = 0xFE;
	tcp_upload_frame.data.HeadBuf[2] = 0x68;
	tcp_upload_frame.data.HeadBuf[3] = 0x20;
	for (int i = 0; i < 7; i++)
	{
		tcp_upload_frame.data.Addr[i] = Sys_data_object.P1.met_addr[i];
	}
	tcp_upload_frame.data.Ctrl = 0x81;
	tcp_upload_frame.data.Num = 0;//59;
	tcp_upload_frame.data.DataFlag[0] = 0x90;
	tcp_upload_frame.data.DataFlag[1] = 0x1F;
	tcp_upload_frame.data.Ser = 0x00;
	tcp_upload_frame.data.Data1Buf[0] = 1;
	tcp_upload_frame.data.Data1Buf[1] = 1;
	tcp_upload_frame.data.Data1Buf[2] = 1;
	tcp_upload_frame.data.Data1Buf[3] = 1;
	//单户户号
	tcp_upload_frame.data.Data2Buf[0] = Sys_data_object.P1.met_addr[0];
	tcp_upload_frame.data.Data2Buf[1] = Sys_data_object.P1.met_addr[1];
	tcp_upload_frame.data.Data2Buf[2] = Sys_data_object.P1.met_addr[2];
	tcp_upload_frame.data.Data2Buf[3] = Sys_data_object.P1.met_addr[3];
	//剩余流量
	tcp_upload_frame.data.Data2Buf[4] = 0x00;//小数位
	tcp_upload_frame.data.Data2Buf[5] = 0x01;
	tcp_upload_frame.data.Data2Buf[6] = 0x00;
	tcp_upload_frame.data.Data2Buf[7] = 0x00;
	//累计流量
	tmp_float.gp22_u32  = Gp30CheckDataApp(2);
	tmp_datas_buf.datas = HexToBcd32((u32)(tmp_float.gp22_float)); 
	tcp_upload_frame.data.Data2Buf[8] = tmp_datas_buf.data_buf[0];//小数位
	tcp_upload_frame.data.Data2Buf[9] = tmp_datas_buf.data_buf[1];
	tcp_upload_frame.data.Data2Buf[10] = tmp_datas_buf.data_buf[2];
	tcp_upload_frame.data.Data2Buf[11] = tmp_datas_buf.data_buf[3];//小数位
	//瞬时流量
	tmp_datas_buf.datas = Gp30CheckDataApp(GP30_APP_INS_FLOW); //瞬时流量(四位小数，放大100000倍)//BCD
	tmp_datas_buf.datas = Gp30DataToBcd(tmp_datas_buf.datas, 10); 
	tcp_upload_frame.data.Data2Buf[12] = tmp_datas_buf.data_buf[0];
	tcp_upload_frame.data.Data2Buf[13] = tmp_datas_buf.data_buf[1];
	tcp_upload_frame.data.Data2Buf[14] = tmp_datas_buf.data_buf[2];//小数位
	tcp_upload_frame.data.Data2Buf[15] = tmp_datas_buf.data_buf[3];
	//温度
	float tmep = TempCheckValueApp();      //							
	if(tmep <0)
	{				
		tmp_datas_buf.datas = (u32)(tmep*(-100));	
		tmp_datas_buf.datas &= 0x0FFFF;
		tmp_datas_buf.datas |= 0x80000;
	}
	else
	{
		tmp_datas_buf.datas = (u32)(tmep*(100));	
		tmp_datas_buf.datas &= 0x7FFFF;
	}
	tcp_upload_frame.data.Data2Buf[16] = tmp_datas_buf.datas_map.data0;
	tcp_upload_frame.data.Data2Buf[17] = tmp_datas_buf.datas_map.data1;
	tcp_upload_frame.data.Data2Buf[18] = tmp_datas_buf.datas_map.data2;//小数位
	//累计工作时间
	tmp_datas_buf.datas = RtccGetWorkHourApp(); 
	tmp_datas_buf.datas = HexToBcd32(tmp_datas_buf.datas);
	tcp_upload_frame.data.Data2Buf[19] = tmp_datas_buf.datas_map.data0;
	tcp_upload_frame.data.Data2Buf[20] = tmp_datas_buf.datas_map.data1;
	tcp_upload_frame.data.Data2Buf[21] = tmp_datas_buf.datas_map.data2;
	//状态字转换
	temp_state = FrameGetByte();
	tcp_stat.statTCP1 = 0;
	tcp_stat.statTCP2 = 0;
	tcp_stat.statTcp1bits.reverse = temp_state.stat1bits.reverse;
	tcp_stat.statTcp1bits.low_flow_rate = temp_state.stat1bits.low_flow_rate;
	tcp_stat.statTcp1bits.valve_state = temp_state.stat1bits.valve_state;
	if(temp_state.stat0bits.transducer_aging)
	{
		tcp_stat.statTcp2bits.amplitude = 0;//低振幅
	}
	else
	{
		tcp_stat.statTcp2bits.amplitude = 3;//高振福
	}
	tcp_stat.statTcp2bits.low_power = temp_state.stat1bits.low_battery_voltage;
	
	tcp_upload_frame.data.Data2Buf[22] = tcp_stat.statTCP1;
	tcp_upload_frame.data.Data2Buf[23] = tcp_stat.statTCP2;
	#if defined(VALVE)
	temp_data = ValveGetStateApp();
	if(temp_data == 0x01)//阀门关
	{
		tcp_upload_frame.data.Data2Buf[22] |= 0x40;
	}
	else//阀门异常
	{
		tcp_upload_frame.data.Data2Buf[22] |= 0xC0;
	}
	#endif
	//信号强度
	NbiotGetCSQ(&temp_data); 
	tcp_upload_frame.data.Data3Buf[0] = 0;
	tcp_upload_frame.data.Data3Buf[1] = temp_data;

	//维度//37.30907
	tcp_upload_frame.data.Data3Buf[2] = 0x03;
	tcp_upload_frame.data.Data3Buf[3] = 0x7F;
	tcp_upload_frame.data.Data3Buf[4] = 0x30;
	tcp_upload_frame.data.Data3Buf[5] = 0x90;
	tcp_upload_frame.data.Data3Buf[6] = 0x70;
	//经度//117.1571
	tcp_upload_frame.data.Data3Buf[7] = 0x11;
	tcp_upload_frame.data.Data3Buf[8] = 0x7F;
	tcp_upload_frame.data.Data3Buf[9] = 0x15;
	tcp_upload_frame.data.Data3Buf[10] = 0x71;
	tcp_upload_frame.data.Data3Buf[11]= 0x00;
	//太阳能电压
	tcp_upload_frame.data.Data3Buf[12]= 0x00;
	tcp_upload_frame.data.Data3Buf[13]= 0x00;//小数位
	//电池电压
	//获取电压值
	temp_bat_val.datas =HexToBcd16(PowerCheckValueSys());	
	tcp_upload_frame.data.Data3Buf[14]= temp_bat_val.datas&0xFF;//小数位
	tcp_upload_frame.data.Data3Buf[15]= (temp_bat_val.datas>>8)&0xFF;
	//压力
	tcp_upload_frame.data.Data3Buf[16]= 0x00;
	tcp_upload_frame.data.Data3Buf[17]= 0x00;
	//版本号
	tcp_upload_frame.data.Data3Buf[18]= (FrameCheckParaApp(FramePara_ProgVersion)>>16)&0xFF;
	tcp_upload_frame.data.Data3Buf[19]= (FrameCheckParaApp(FramePara_ProgVersion)>>24)&0xFF;
	//日期时间
	RtccGetDateTime(&tempRtccTime);//上报时间
	tcp_upload_frame.data.Data3Buf[20] = tempRtccTime.s.second;
	tcp_upload_frame.data.Data3Buf[21] = tempRtccTime.s.minute;
	tcp_upload_frame.data.Data3Buf[22] = tempRtccTime.s.hour;
	tcp_upload_frame.data.Data3Buf[23] = tempRtccTime.s.day;
	tcp_upload_frame.data.Data3Buf[24] = tempRtccTime.s.month;
	tcp_upload_frame.data.Data3Buf[25] = tempRtccTime.s.year; 
	tcp_upload_frame.data.Data3Buf[26] = 0x20;
	//状态
	tcp_upload_frame.data.Data3Buf[27] = 0x00;
	//校验和
	tcp_upload_frame.data.Cs = 0;
	for(i=2;i<72;i++)
	{
		tcp_upload_frame.data.Cs += tcp_upload_frame.buf[i];
	}
	tcp_upload_frame.data.End = 0x16;
	
	for(i=0;i<74;i++)
	{
		*p_send_buf++ = tcp_upload_frame.buf[i];
	}
	*p_send_len = 74;
}

void GetUploadDataResetState_SH(void)
{
	upload_frame_stat_sh =UP_DEAL_S0;
	upload_task_complete_sh = PTL_PACK_BUSY;
}
u8 GetUploadDataCheckIdle_SH(void)
{
	if(UP_DEAL_S0 == upload_frame_stat_sh)
    {
        return TASK_IDLE;
    }
    else
    {
        return TASK_BUSY;
    }
}
u8 GetUploadDataCheckTask_SH(void)
{
	return upload_task_complete_sh;
}

void GetUploadDataMachine_SH(u8 data_step, u8* p_send_buf, u16* p_send_len)
{
	switch(upload_frame_stat_sh)
	{
		case UP_DEAL_S0:
		{
			if(data_step == UPLOAD_FRAME_REQUEST_NEW)
			{
				temp_upload_step = 0;
				upload_frame_retry_times = 0;
				upload_frame_stat_sh = UP_DEAL_S1;//发送注册包
			}
			else if(data_step == UPLOAD_FRAME_UPLOAD_OK)//发送数据成功,开始立即发送心跳包
			{
				SystemClearUploadAgain();//重传清0
				upload_frame_stat_sh = UP_DEAL_S3;//发第一个心跳包
			}
			else if(data_step == UPLOAD_FRAME_UPLOAD_RETRY)//重发数据,或者是发送了注册包
			{
				if(temp_upload_step == UP_DEAL_S1)//注册包
				{
					upload_frame_stat_sh = UP_DEAL_S20;//发送数据包
				}
				else if(temp_upload_step == UP_DEAL_S20)//数据包
				{
					upload_frame_stat_sh = UP_DEAL_S21;//重试
				}
				else if(temp_upload_step == UP_DEAL_S3)//发第一个心跳包
				{
					upload_frame_stat_sh = UP_DEAL_S4;//再次延时发送心跳包
				}
				else//第二个心跳包或其他情况
				{
					upload_task_complete_sh = PTL_PACK_FAIL;
					upload_frame_stat_sh = UP_DEAL_S0;
				}
			}
			else if(data_step == UPLOAD_FRAME_ONLINE_FAIL) //联网失败
			{
				  if(UPLOAD_TYPE_FIX_TIME == GetEventUploadType()||
					(UPLOAD_TYPE_RETRY_AGAIN == GetEventUploadType()))//定时上传
				{
					SystemAddUploadAgain();//重传增加
				}
				upload_task_complete_sh = PTL_PACK_FAIL;
				upload_frame_stat_sh = UP_DEAL_S0;
			}
			else 
			{
				upload_task_complete_sh = PTL_PACK_FAIL;
				upload_frame_stat_sh = UP_DEAL_S0;
			}
		}
		break;
		case UP_DEAL_S1://组注册帧
		{
			if(EepIfIdle())
			 {
				temp_upload_step = UP_DEAL_S1;
				Register_TcpFrameData(p_send_buf, p_send_len);
				upload_task_complete_sh = PTL_PACK_SUCCESS;//成功
				upload_frame_stat_sh = UP_DEAL_S0;
			 }   
		}
		break;
		case UP_DEAL_S20://组上报帧
		{
			temp_upload_step = UP_DEAL_S20;
			Upload_TcpFrameData(p_send_buf, p_send_len);
			upload_task_complete_sh = PTL_PACK_SUCCESS;//成功
			upload_frame_stat_sh = UP_DEAL_S0;
		}
		break;
		case UP_DEAL_S21://重试
		{
			if(upload_frame_retry_times < 3) 
			{
				upload_frame_retry_times++;
				upload_frame_stat_sh = UP_DEAL_S20;
			} 
			else//重新发送失败3次的处理
			{
				if((UPLOAD_TYPE_FIX_TIME == GetEventUploadType())||   //重传
					(UPLOAD_TYPE_RETRY_AGAIN == GetEventUploadType()))//定时上传
				{
					SystemAddUploadAgain();//重传增加
				}
				upload_task_complete_sh = PTL_PACK_FAIL;
				upload_frame_stat_sh = UP_DEAL_S0;
			}
		}
		break;
		
		case UP_DEAL_S3://立即发送心跳包获取下行指令
		{
		    temp_upload_step = UP_DEAL_S3;
			Ping_TcpFrameData(p_send_buf, p_send_len);
			upload_task_complete_sh = PTL_PACK_SUCCESS;//成功
			upload_frame_stat_sh = UP_DEAL_S0;  
		}
		break;
		case UP_DEAL_S4://间隔1分钟再发送心跳包
		{
			temp_upload_step = UP_DEAL_S4;
			Ping_TcpFrameData(p_send_buf, p_send_len);
			Set100msTimer(TIMER_100MS_UPLOAD_MONITOR, 600);//定时60秒
			upload_frame_stat_sh = UP_DEAL_S5;  
		}
		break;
		case UP_DEAL_S5://等待延时时间到
		{
			if(0 == Check100msTimer(TIMER_100MS_UPLOAD_MONITOR))
			{
				upload_task_complete_sh = PTL_PACK_SUCCESS;//成功
				upload_frame_stat_sh = UP_DEAL_S0;
			}
			if(FrameCheckMsgApp(MsgNbUpload_OffLine)) //立即下线消息
			{
				FrameClearMsgApp(MsgNbUpload_OffLine);
				upload_task_complete_sh = PTL_PACK_FAIL;//结束
				upload_frame_stat_sh = UP_DEAL_S0;
			}
		}
		break;
		
		default:
		{
			upload_task_complete_sh = PTL_PACK_FAIL;
			upload_frame_stat_sh = UP_DEAL_S0;
		}
		break;
	}
}
/*******************************************************************************
 * @fun_name:NB_SS_Control_GetPara
 * @brief   :    
 * @param[in] :读取上报控制相关参数
 * @param[out]: None
 * @retval    : None
 * @other     :
 ******************************************************************************/
u8 NB_SS_Control_GetPara(NB_SS_ControlParaTypeDef paraType)
{
    switch(paraType)
	{
	    case NB_HistroyReadIndex://历史数据的读指针
		{
			return Sys_data_object.P1.histroy_w;
		}
		case NB_UploadFailTimes://失败次数
		{
			u8 temp_fail_times=0;
			for(int i = 0; i < 32; i++)
			{
				if(((Sys_data_object.P1.Supplemental_send_flag.datas  >> i) & 0x00000001) == 0x00000001)
				{
					temp_fail_times += 1;
				}
			}
			return temp_fail_times;
		}
		default:
			break;
	}
	return 0;
}
/*******************************************************************************
 * @fun_name:NB_SS_Control_SetPara
 * @brief   :    
 * @param[in] :设置上报控制相关参数
 * @param[out]: None
 * @retval    : None
 * @other     :
 ******************************************************************************/
void NB_SS_Control_SetPara(NB_SS_ControlParaTypeDef paraType, u8 data)
{
    switch(paraType)
	{
	    case NB_HistroyReadIndex://历史数据的读指针
		{
			Sys_data_object.P1.histroy_w = data;
			break;
		}
		default:
			break;
	}
}


//规约数据存储部分初始化
void DataStoreInit(void)
{
	Quanzhou_Store_InitApp();
}
//规约数据存储状态机
void DataStoreMachine(void)
{
	Quanzhou_Store_Machine();//冻结数据存储
}
//规约数据存储休眠判断
u8 DataStoreIfIdle(void)
{
    if(QuanzhouStore_IfSleep()==TRUE)
    {
        return TRUE;
    }
    return FALSE;
}

#endif



