#ifndef IEC104_LINK_SRV_123_INCLUDED #define IEC104_LINK_SRV_123_INCLUDED #ifdef __cplusplus extern "C" { #endif /************************************************************************/ #include "iec104_apdu.h" #include "general_function.h" #include "general_socket.h" #include "general_serial.h" #include "general_can.h" //发送命令(或命令的返回)缓冲区的长度 #define IEC104_SEND_CMD_BUFFER_MAX_COUNT 224 //cbt modified 2021.7.2 为了防止事件报告频繁产生从而生成大量事件报告报文,占满缓冲区,导致故障报告报文不能放入缓冲区,将缓冲区扩大一倍 //重要的一级数据缓冲区(15个装置,总召每个4条) #define IEC104_SEND_URGENT_BUFFER_MAX_COUNT 192//96 //次要的二级数据缓冲区 #define IEC104_SEND_GENERAL_BUFFER_MAX_COUNT 64 typedef enum { IEC104_I_ASDU_TYPE_CMD=0, IEC104_I_ASDU_TYPE_URGENT, IEC104_I_ASDU_TYPE_GENERAL } IEC104_I_ASDU_TYPE; /*************2011.10.26增加一些表示链路连接状态的定义****************************/ typedef enum{ IEC104_LINK_STATUS_SRV_IDLE=0, //空闲,表示连接还没有建立 IEC104_LINK_STATUS_SRV_OK, //可以发送测试侦,但不能发送I帧 //下面两个仅服务器端用到 IEC104_LINK_STATUS_SRV_START_RECV } IEC104_LINK_STATUS_SRV; /********收到的每个客户端连接,对应下面一个结构体*******/ typedef struct { FLAG_LINK flagLink; //用于通知外部,//未启动或停止时置0,可以传输I时置1, IEC104_LINK_PROPER link_proper; struct { //启动发送控制,需要建立发送缓冲区(根据命令等级,需要划分几个命令缓冲区) ST_INT send_cmd_readIP; ST_INT send_cmd_writeIP; ST_UCHAR send_cmd_Buffer[IEC104_SEND_CMD_BUFFER_MAX_COUNT][IEC104_APDU_MAX_LEN]; ST_INT send_urgent_readIP; ST_INT send_urgent_writeIP; ST_UCHAR send_urgent_Buffer[IEC104_SEND_URGENT_BUFFER_MAX_COUNT][IEC104_APDU_MAX_LEN]; ST_INT send_general_readIP; ST_INT send_general_writeIP; ST_UCHAR send_general_Buffer[IEC104_SEND_GENERAL_BUFFER_MAX_COUNT][IEC104_APDU_MAX_LEN]; } link_send_buffer; struct { IEC104_LINK_STATUS_SRV linkStatus; ST_UINT16 IcountRecv; ST_UINT16 IcountSend; ST_UINT16 IcountLocalUnConfirm; //收到但未确认的I数量 ST_UINT16 IcountRemoteConfirm; //本变量使用,启动了发送传输控制 ST_UINT16 IcountmaxSend; //未确认的情况下,最大发送的I帧数量 12*2 ST_UINT16 IcountmaxToConfirm; //收到I帧,超时或本次数已到,发送确认帧 8*2 ST_DOUBLE record_time_t0; //104中从站不判断T0(建立连接超时) ST_DOUBLE space_t0; //30 ST_DOUBLE record_time_t1_test; //发送测试帧启动, 停止:收到测试确认 ST_DOUBLE record_time_t1_I; //记录:发I启动,停止:收到I确认 ST_DOUBLE space_t1; //15 ST_DOUBLE record_time_t2; //记录:收到I启动,停止:发送I,发送确认 ST_DOUBLE space_t2; //10 ST_DOUBLE record_time_t3; //记录:发送,收到帧, 到时间后发送测试帧 ST_DOUBLE space_t3; //20 } link_records; struct { IEC104_LINK_TYPE link_type; union { SOCKET_LINK_ATTRIB *sock_attrib; //这里必须定义为指针,初始化的时候,为它赋一个位置 SERIAL_ATTRIB *serial_attrib; //串口连接参数 CAN_LINK_ATTRIB *can_link; //CAN连接参数 } u; //下面的指针类型可能是TCP 串口 或 CAN ST_VOID *iec104_service_srv; //保存本指针, 收到I的时候确认交给哪个服务器 ST_INT monitorChannel; //调试数据的通道号 } link_attrib; } IEC104_LINK_SRV; /***发送数据的时候,调用这个函数,将数据放到指定缓冲区中***/ ST_RET iec104_link_srv_save_asdu( IEC104_LINK_SRV *iec104_link_srv, ST_UCHAR *asdu, ST_INT asduLen, IEC104_I_ASDU_TYPE type ); /***初始化连接属性值***/ ST_RET iec104_link_srv_property_init( IEC104_LINK_SRV * iec104_link ); ST_RET iec104_link_srv_property_set( IEC104_LINK_SRV * iec104_link, IEC104_LINK_TYPE link_type, ST_VOID *link_attrib, ST_VOID *iec104_service_srv, ST_INT monitorChl ); /*** 释放连接 ***/ ST_RET iec104_link_srv_property_release( IEC104_LINK_SRV * iec104_link ); /***循环调用本函数,处理接收缓冲中的数据(调用服务层函数),发送发送缓冲中的I侦**/ ST_INT iec104_link_srv_check_status( IEC104_LINK_SRV *iec104_link ); /************************************************************************/ #ifdef __cplusplus } #endif #endif