#ifndef __PUBLIC_H
#define	__PUBLIC_H

#include "bsp.h"

#define	LORA_LOWPOWER			//LORA低功耗设备，采用主动上报方式

#define	SENSOR_DATA_LEN_MAX										50
#define	SENSOR_NUM_MAX												16
#define	COMMUNIT_MUM_MAX											32

#define	REGISTER_INTERVAL_MAX									(2 * 60)
#define	COMMUNIT_READ_SENSOR_INTERVAL_MAX			(1 * 60)

#define	LORA_CAT_ERR_RESET_DLY_MAX						(20 * 60)		//单位秒

typedef struct GateWay_t GateWayPara_t, *GateWayPara;

typedef void (*SendData)(uint8_t *sData, uint16_t sLen);
typedef int (*DataRevCallBack)(GateWayPara GateWay, uint8_t *rData, uint16_t rLen);
typedef int (*DataRevResCallBack)(GateWayPara GateWay, uint8_t *rData, uint16_t rLen, SendData Response);
typedef int (*SendDataOrg)(uint8_t *sData);

typedef enum {
	DEBUG_CH_DBG,
	DEBUG_CH_RS485_1,
	DEBUG_CH_RS485_2,
}DebugChannel_m;


typedef enum {
	DEV_TYPE_BROADCAST,
	DEV_TYPE_INC_COMMUNIT = 0x8001,
	DEV_TYPE_EXT_COMMUNIT,
	DEV_TYPE_ICE_SENSOR,
	DEV_TYPE_CRACK_SENSOR,
	DEV_TYPE_PRESSURE_SENSOR,
	DEV_TYPE_RAIN_SENSOR,
}DevType_m;

typedef enum {
	CATONE_COMM,
	ETH_COMM,
}CommType_m;

typedef enum {
	LORA_COMM,
	RS485CH1_COMM,
	RS485CH2_COMM
}SensorComm_m;

typedef enum {
	SENSOR_TYPE_NULL,
	STRAIN_SENSOR,
	PRESSURE_SENSOR,
	SONAR_SENSOR,
	CAP_SENSOR,
	VIBRATE_SENSOR,
	DEFM_3D_SENSOR,
	STRAIN_SENSOR_MAG = 8,
	PRESSURE_SENSOR_MAG,
	SONAR_SENSOR_MAG,
	CAP_SENSOR_MAG,
	DEFM_3D_SENSOR_MAG,
	STRAIN_2_SENSOR,
	CRACK_SENSOR,
	SIX_DIM_SENSOR,
	POSTURE_SENSOR,
	LASER_DISTANCE_SENSOR,
	CRACK_2_SENSOR,			//裂缝别名
}SensorType_m;

typedef enum {
	COMM_UNIT_CMD_REG,
	COMM_UNIT_CMD_CAIL,
	COMM_UNIT_CMD_READ,
	COMM_UNIT_CMD_SET_SENSOR_COLL_TIME = 5,
	COMM_UNIT_CMD_TIME_SYNC,
	COMM_UNIT_CMD_END,
}CommUnitCmd_m;

typedef enum {
	NET_COMM_CMD_REG,
	NET_COMM_CMD_CAIL,
	NET_COMM_CMD_UPDATE,
	NET_COMM_CMD_READ_GW_INFO,
	NET_COMM_CMD_READ_UNIT_INFO,
	NET_COMM_CMD_HIS_DATA,
	NET_COMM_CMD_ADD_UNIT,
	NET_COMM_CMD_LP_DEV_CONFIG,
	NET_COMM_CMD_END,
}NetCommCmd_m;

typedef struct {
	int16_t AccX;
	int16_t AccY;
	int16_t AccZ;
	int32_t Strain1;
	int32_t Strain2;
	int32_t Strain3;
	int32_t Strain4;
	int32_t Strain5;
}__attribute__((packed))StrainSensorType_t;

typedef struct {
	int16_t AccX;
	int16_t AccY;
	int16_t AccZ;
	int16_t MegX;
	int16_t MegY;
	int16_t MegZ;	
	int32_t Strain1;
	int32_t Strain2;
	int32_t Strain3;
	int32_t Strain4;
	int32_t Strain5;
	int32_t Strain6;
}__attribute__((packed))StrainMegSensorType_t;

typedef struct {
	int16_t AccX;
	int16_t AccY;
	int16_t AccZ;
	uint32_t Pressure;
}__attribute__((packed))PressureSensorType_t;

typedef struct {
	int16_t AccX;
	int16_t AccY;
	int16_t AccZ;
	uint16_t Sonar1;
	uint16_t Sonar2;
	uint16_t Sonar3;
	uint16_t Sonar4;
}__attribute__((packed))SonarSensorType_t;

typedef struct {
	int16_t AccX;
	int16_t AccY;
	int16_t AccZ;
	uint16_t Capacitance1;
	uint16_t Capacitance2;
}__attribute__((packed))CapSensorType_t;

typedef struct {
	int16_t AccX;
	int16_t AccY;
	int16_t AccZ;
}__attribute__((packed))Defm3DSensorType_t;

typedef struct {
	int16_t AccX;
	int16_t AccY;
	int16_t AccZ;
	int16_t MegX;
	int16_t MegY;
	int16_t MegZ;	
}__attribute__((packed))Defm3DMegSensorType_t;

typedef struct {
	int16_t AccX;
	int16_t AccY;
	int16_t AccZ;
	int16_t MagX;
	int16_t MagY;
	int16_t MagZ;
	int32_t Strain1;
	int32_t Strain2;
	int32_t Strain3;
	int32_t Strain4;
	int32_t Strain5;
	int32_t Strain6;
}__attribute__((packed))StrainMagSensorType_t;

typedef struct {
	int16_t AccX;
	int16_t AccY;
	int16_t AccZ;
	int16_t MagX;
	int16_t MagY;
	int16_t MagZ;
	uint32_t Pressure;
}__attribute__((packed))PressureMagSensorType_t;

typedef struct {
	int16_t AccX;
	int16_t AccY;
	int16_t AccZ;
	int16_t MagX;
	int16_t MagY;
	int16_t MagZ;
	uint16_t Sonar1;
	uint16_t Sonar2;
	uint16_t Sonar3;
	uint16_t Sonar4;
}__attribute__((packed))SonarMagSensorType_t;

typedef struct {
	int16_t AccX;
	int16_t AccY;
	int16_t AccZ;
	int16_t MagX;
	int16_t MagY;
	int16_t MagZ;
	uint16_t Capacitance1;
	uint16_t Capacitance2;
}__attribute__((packed))CapMagSensorType_t;

typedef struct {
	int16_t AccX;
	int16_t AccY;
	int16_t AccZ;
	int16_t MagX;
	int16_t MagY;
	int16_t MagZ;
}__attribute__((packed))Defm3DMagSensorType_t;

typedef struct {
	int16_t AccX;
	int16_t AccY;
	int16_t AccZ;
	int32_t Strain1;
	int32_t Strain2;
}__attribute__((packed))Strain2SensorType_t;

typedef struct {
	int16_t AccX_L;
	int16_t AccY_L;
	int16_t AccZ_L;
	int16_t MagX_L;
	int16_t MagY_L;
	int16_t MagZ_L;
	int16_t AccX_R;
	int16_t AccY_R;
	int16_t AccZ_R;
	int16_t MagX_R;
	int16_t MagY_R;
	int16_t MagZ_R;
}__attribute__((packed))CrackSensorType_t;

typedef struct {
	int16_t PitchAngle;
	int16_t RollAngle;
	int16_t VibrationStrength;
	int16_t Temperature;
}__attribute__((packed))PostureSensorType_t;

typedef struct {
	uint8_t CommDevAddr[6];			//通讯单元地址
	uint16_t CollectInterval;		//采集时间间隔
	uint16_t ReportInterval;		//上报时间间隔
	uint8_t ERInterval;				//紧急上报时间间隔
	uint8_t ERTime;						//紧急上报时长
}__attribute__((packed))SvrDownLPDevConfigPara_t;

typedef struct {
	int Distance;
}__attribute__((packed))LaserDistanceSensorType_t;


#define	LW_DEV_COLLECT_INTERVAL_MAX					300
#define	LW_DEV_REPORT_INTERVAL_MAX					20
#define	LW_DEV_ER_INTERVAL_MAX							2
#define	LW_DEV_ER_TIME_MAX									20

typedef struct {
	uint16_t CollectInterval;		//采集时间间隔
	uint16_t ReportInterval;		//上报时间间隔
	uint8_t ERInterval;				//紧急上报时间间隔
	uint8_t ERTime;						//紧急上报时长
	uint32_t TimeStamp;				//时间戳
}__attribute__((packed))LPDevConfigPara_t;

typedef struct {
	bool RegFlag;
	bool RevNewDataFlag;
	bool CommStatus;	//通讯状态，1-在线，0-离线
	uint8_t BatLevel;
	uint32_t CommErrCnt;
	uint8_t Mac[6];
	uint16_t CUType;
	uint8_t SensorN;
	uint16_t SensorType[SENSOR_NUM_MAX];
	//低功耗设备配置信息
	bool ConfigFlag;			//配置标志，为1表示有新配置，应答低功耗设备时需要附带发送
	uint16_t CollectInterval;		//采集时间间隔
	uint16_t ReportInterval;		//上报时间间隔
	uint8_t ERInterval;				//紧急上报时间间隔
	uint8_t ERTime;						//紧急上报时长
}CommUnitPara_t, *CommUnitPara;

typedef struct {
	uint8_t Data[SENSOR_NUM_MAX][SENSOR_DATA_LEN_MAX];
}CommUnitData_t, *CommUnitData;

typedef struct {
	CommUnitPara_t Para;
	CommUnitData_t SensorData;
}CommUnit_t, *CommUnit;

typedef struct {
	bool Enable;		//串口使能
	bool CommUnitEnable;		//通讯单元使能，开启（使用内部通讯单元功能，直接和传感器通讯），关闭（直接和RS485类型的通讯单元通讯）
	bool QuerySensorFlag;		//查询传感器标志
	uint8_t Power;
	uint32_t BaudRate;
	SendData RS485Send;
	CommUnit_t CUData;
}RS485Para_t, *RS485Para;

typedef struct {
	uint8_t Header;
	uint8_t GWMac[6];
	uint8_t DevMac[6];
	uint8_t Cmd;
	uint16_t DevType;
	uint8_t PayloadLen;
}__attribute__((packed))CommUnitFrameHeader_t, *CommUnitFrameHeader;

typedef struct {
	uint8_t Header;
	uint8_t GWMac[6];
	uint8_t SvrMac[6];
	uint8_t Cmd;
	uint32_t Timestamp;
	uint8_t PacketNum;
	uint8_t PacketIdx;
	uint16_t PayloadLen;
}__attribute__((packed))NetCommFrameHeader_t, *NetCommFrameHeader;

typedef struct {
	uint8_t ucChannel;
	int8_t ucPower;
	uint8_t SignalBw;
	uint8_t SpreadFactor;
	uint8_t ErrorCoding;
	uint8_t RegPreamble;
}LoraPara_t, *pLoraPara;

typedef struct {
	uint32_t SavFlag;									//存储标志
	CommType_m Comm;									//网关通讯方式
	uint8_t GwMac[6];									//网关mac
	char SvrAddr[4];									//服务器地址
	uint32_t SvrPort;									//服务器端口
	uint32_t CommUnitReadInterval;		//通讯单元读取时间间隔,单位S
	CommUnitPara_t CommUnitArray[COMMUNIT_MUM_MAX];			//注册的通讯单元信息
	RS485Para_t Rs485Ch1;							//RS485通道1配置
	RS485Para_t Rs485Ch2;							//RS485通道2配置
	LoraPara_t Lora;									//Lora配置
}GWConfigPara_t, *GWConfigPara;

struct GateWay_t{
	uint8_t DebugChannel;
	bool TimeSyncFlag;								//时间同步标志
	bool SvrRegFlag;									//服务器注册标志
	uint8_t SvrMac[6];								//服务器mac
	GWConfigPara_t ConfigPara;				//配置参数
	CommUnitData_t CUDataArray[COMMUNIT_MUM_MAX];
	uint8_t Battery;									//电池电量
	uint32_t HistoryNum;							//历史数据数量
	DataRevCallBack SvrRevCallBack;		//接收到服务器回调
	DataRevResCallBack CommUnitRevCallBack;	//通讯单元接收回调
	rt_mq_t NetSendData_MQ;						//网络发送数据队列，第一个字节用于存储消息长度, 第二字节存储命令字，后为数据
	rt_mq_t LoraRev_MQ;								//Lora接收消息队列，第一个字节用于存储消息长度，后为数据
	rt_mutex_t UartRevMutex;
};

int Cat1EthRevCallBack(GateWayPara GateWay, uint8_t *rData, uint16_t rLen);
uint16_t CRC_Modbus(uint16_t wBase, __IO uint8_t *para, uint16_t length);
uint8_t AsciiToHex(char *ASCData, uint8_t *HexData, uint8_t sLen);
void HexToAscii(uint8_t *HexData, char *ASCData, uint8_t sLen);
int NetCommOrgData(GateWayPara GateWay, uint8_t *MegData, uint8_t *OutData);
int CommUnitAnalyze(GateWayPara GateWay, uint8_t *rData, uint16_t rLen, SendData Response);
void DebugAnalyze(GateWayPara GateWay, uint8_t *rData, uint16_t rLen);
void CommUnitCmdSend(GateWayPara GateWay, uint8_t *CommUnitMac, CommUnitCmd_m Cmd, uint8_t *Payload, uint16_t PayloadLen, SendData Send);
int CheckCommUnitReg(GateWayPara GateWay, uint8_t *CommUnitMac);
int CommUintOrgData(GateWayPara GateWay, CommUnitPara CUPara, CommUnitData CUData, uint8_t *sData);
void DebugDisplaySensorData(int SensorIdx, uint16_t SensorType, uint8_t *SensorData);
#endif

