<修改> 1、增加mms服务端配置文件,并解析;
2、增加mms服务端配置信息的处理; 3、调整mms配置文件的目录
This commit is contained in:
parent
15ecc786bc
commit
3743b69ef2
|
|
@ -146,7 +146,7 @@ typedef struct
|
||||||
std::string saddr;
|
std::string saddr;
|
||||||
uint8_t status;
|
uint8_t status;
|
||||||
uint32_t sec;
|
uint32_t sec;
|
||||||
uint16_t ums;
|
uint16_t ms;
|
||||||
}stru_dc_soe;
|
}stru_dc_soe;
|
||||||
|
|
||||||
typedef struct
|
typedef struct
|
||||||
|
|
|
||||||
|
|
@ -106,67 +106,49 @@ extern "C" {
|
||||||
#define MMS_S_PARAM_MAX 16
|
#define MMS_S_PARAM_MAX 16
|
||||||
|
|
||||||
|
|
||||||
|
typedef void (*mms_s_value_update_cb)(const char * saddr, const char * val);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 参数/定值/控制的基础信息结构体
|
* @brief 注册值更新回调函数
|
||||||
* @field saddr 短地址(映射到 IEC61850 模型中的 sAddr 属性)
|
* @param cb 值更新回调函数指针
|
||||||
* @field desc 描述信息
|
|
||||||
* @field type 数据类型(对应 DATA_TYPE_* 枚举)
|
|
||||||
* @field ctrl_model 控制模型类型
|
|
||||||
*/
|
*/
|
||||||
|
void mms_s_value_update_register(mms_s_value_update_cb *cb);
|
||||||
|
|
||||||
|
|
||||||
typedef struct
|
typedef struct
|
||||||
{
|
{
|
||||||
char saddr[MMS_S_STR_LEN];
|
char saddr[MMS_S_STR_LEN];
|
||||||
char desc[MMS_S_STR_LEN];
|
char desc[MMS_S_STR_LEN];
|
||||||
uint8_t type;
|
uint8_t type;
|
||||||
uint8_t ctrl_model;
|
uint8_t ctrl_model;
|
||||||
}stru_mms_s_param_base;
|
}stru_mms_s_signal_base;
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 定值数据结构体(一个定值点对应一个数据值)
|
|
||||||
* @field base 基础信息(saddr / desc / type)
|
|
||||||
* @field data 指向实际数据值的指针
|
|
||||||
*/
|
|
||||||
typedef struct
|
typedef struct
|
||||||
{
|
{
|
||||||
stru_mms_s_param_base base;
|
stru_mms_s_signal_base base;
|
||||||
void *data;
|
void *p_data;
|
||||||
}stru_mms_s_setting;
|
}stru_mms_s_setting;
|
||||||
|
|
||||||
/** 定值回调函数类型:当定值被写入时调用 */
|
|
||||||
typedef void (*mms_s_setting_cb)(stru_mms_s_setting *p_setting, const char *p_data);
|
typedef void (*mms_s_setting_cb)(stru_mms_s_setting *p_setting, const char *p_data);
|
||||||
|
|
||||||
/**
|
|
||||||
* 参数数据结构体(一个参数点可对应多个定值区的值)
|
|
||||||
* @field base 基础信息(saddr / desc / type)
|
|
||||||
* @field param_num 有效参数组数量
|
|
||||||
* @field data 各组参数数据指针数组,最多 MMS_S_PARAM_MAX 个
|
|
||||||
*/
|
|
||||||
typedef struct
|
typedef struct
|
||||||
{
|
{
|
||||||
stru_mms_s_param_base base;
|
stru_mms_s_signal_base base;
|
||||||
uint8_t param_num;
|
uint8_t param_num;
|
||||||
void *data[MMS_S_PARAM_MAX];
|
void *p_data[MMS_S_PARAM_MAX];
|
||||||
}stru_mms_s_param;
|
}stru_mms_s_param;
|
||||||
|
|
||||||
/** 参数回调函数类型:当参数区切换或被确认时调用 */
|
|
||||||
typedef void (*mms_s_param_cb)(stru_mms_s_param *p_param, const char *p_data, int setting_zone);
|
typedef void (*mms_s_param_cb)(stru_mms_s_param *p_param, const char *p_data, int setting_zone);
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 控制对象数据结构体
|
|
||||||
* @field saddr 短地址
|
|
||||||
* @field desc 描述信息
|
|
||||||
* @field ctrl_model 控制模型类型
|
|
||||||
*/
|
|
||||||
typedef struct
|
typedef struct
|
||||||
{
|
{
|
||||||
char saddr[MMS_S_STR_LEN];
|
stru_mms_s_signal_base base;
|
||||||
char desc[MMS_S_STR_LEN];
|
void *p_data;
|
||||||
uint8_t ctrl_model;
|
|
||||||
}stru_mms_s_control;
|
}stru_mms_s_control;
|
||||||
|
|
||||||
/** 控制操作回调函数类型:当控制命令被执行时调用 */
|
|
||||||
typedef void (*mms_s_control_cb)(stru_mms_s_control *p_control, uint8_t state);
|
typedef void (*mms_s_control_cb)(stru_mms_s_control *p_control, uint8_t state);
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -6,7 +6,7 @@
|
||||||
* Direct Operate 控制模型。
|
* Direct Operate 控制模型。
|
||||||
*
|
*
|
||||||
* 【核心结构】
|
* 【核心结构】
|
||||||
* - vec_control : 外部注册的控制对象列表(由 mms_s_control_register() 设置)
|
* - g_vec_control : 外部注册的控制对象列表(由 mms_s_control_register() 设置)
|
||||||
* - cb_control : 控制执行后的回调函数
|
* - cb_control : 控制执行后的回调函数
|
||||||
*
|
*
|
||||||
* 【两个关键回调】
|
* 【两个关键回调】
|
||||||
|
|
@ -29,7 +29,7 @@
|
||||||
#include "mms_s.h"
|
#include "mms_s.h"
|
||||||
|
|
||||||
/** 外部注册的控制对象列表 */
|
/** 外部注册的控制对象列表 */
|
||||||
LOCAL std::vector<stru_mms_s_control> vec_control;
|
LOCAL std::vector<stru_mms_s_control> g_vec_control;
|
||||||
/** 控制操作回调函数 */
|
/** 控制操作回调函数 */
|
||||||
LOCAL mms_s_control_cb cb_control = NULL;
|
LOCAL mms_s_control_cb cb_control = NULL;
|
||||||
|
|
||||||
|
|
@ -116,9 +116,9 @@ LOCAL ControlHandlerResult control_handler(ControlAction action, void* parameter
|
||||||
DataAttribute *stVal = it->p_all_do->map_all_da["stVal"]->DA;
|
DataAttribute *stVal = it->p_all_do->map_all_da["stVal"]->DA;
|
||||||
std::string saddr = it->p_all_do->map_all_da["stVal"]->DA->sAddr;
|
std::string saddr = it->p_all_do->map_all_da["stVal"]->DA->sAddr;
|
||||||
|
|
||||||
for(std::vector<stru_mms_s_control>::iterator it_control = vec_control.begin(); it_control != vec_control.end(); ++it_control)
|
for(std::vector<stru_mms_s_control>::iterator it_control = g_vec_control.begin(); it_control != g_vec_control.end(); ++it_control)
|
||||||
{
|
{
|
||||||
if(it_control->saddr == saddr)
|
if(0 == saddr.compare(it_control->base.saddr))
|
||||||
{
|
{
|
||||||
if(NULL != cb_control)
|
if(NULL != cb_control)
|
||||||
{
|
{
|
||||||
|
|
@ -253,12 +253,12 @@ int mms_s_control_register(stru_mms_s_control *p_control, uint16_t num, mms_s_co
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
vec_control.clear();
|
g_vec_control.clear();
|
||||||
vec_control.reserve(num);
|
g_vec_control.reserve(num);
|
||||||
|
|
||||||
for(uint16_t i = 0; i < num; ++i)
|
for(uint16_t i = 0; i < num; ++i)
|
||||||
{
|
{
|
||||||
vec_control.push_back(p_control[i]);
|
g_vec_control.push_back(p_control[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(NULL != cb)
|
if(NULL != cb)
|
||||||
|
|
@ -285,9 +285,9 @@ int control_init(IedServer server, stru_icd &icd)
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(vec_control.empty())
|
if(g_vec_control.empty())
|
||||||
{
|
{
|
||||||
LOG_E("vec_control is empty");
|
LOG_E("g_vec_control is empty");
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -5,7 +5,7 @@
|
||||||
* @details 定值组(Setting Group)允许多套定值间切换。本模块实现:
|
* @details 定值组(Setting Group)允许多套定值间切换。本模块实现:
|
||||||
*
|
*
|
||||||
* 【数据结构】
|
* 【数据结构】
|
||||||
* - vec_params : 外部注册的参数列表,每个元素包含多组值(param_num 个)
|
* - g_vec_params : 外部注册的参数列表,每个元素包含多组值(param_num 个)
|
||||||
* - g_param_cb : 参数回调函数
|
* - g_param_cb : 参数回调函数
|
||||||
*
|
*
|
||||||
* 【FC=SG vs FC=SE】
|
* 【FC=SG vs FC=SE】
|
||||||
|
|
@ -26,7 +26,7 @@
|
||||||
#include "myMms_s.h"
|
#include "myMms_s.h"
|
||||||
#include "mms_s_param.h"
|
#include "mms_s_param.h"
|
||||||
|
|
||||||
LOCAL std::vector<stru_mms_s_param> vec_params;
|
LOCAL std::vector<stru_mms_s_param> g_vec_params;
|
||||||
|
|
||||||
LOCAL mms_s_param_cb g_param_cb = NULL;
|
LOCAL mms_s_param_cb g_param_cb = NULL;
|
||||||
|
|
||||||
|
|
@ -125,7 +125,7 @@ LOCAL int g_param_update_funcs_count = sizeof(g_param_update_funcs)/sizeof(g_par
|
||||||
/**
|
/**
|
||||||
* 将指定定值组号的参数数据加载到 SG DA
|
* 将指定定值组号的参数数据加载到 SG DA
|
||||||
*
|
*
|
||||||
* 根据 vec_params 中每个参数的 data[actSG-1] 值,找到对应 sAddr+"_SG" 的
|
* 根据 g_vec_params 中每个参数的 data[actSG-1] 值,找到对应 sAddr+"_SG" 的
|
||||||
* 模型节点,将值写入。
|
* 模型节点,将值写入。
|
||||||
*
|
*
|
||||||
* @param ld 逻辑设备
|
* @param ld 逻辑设备
|
||||||
|
|
@ -140,7 +140,7 @@ LOCAL void param_load_active_sg_values(stru_LDevice &ld, int actSG)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
for(std::vector<stru_mms_s_param>::iterator it_param = vec_params.begin(); it_param != vec_params.end(); it_param++)
|
for(std::vector<stru_mms_s_param>::iterator it_param = g_vec_params.begin(); it_param != g_vec_params.end(); it_param++)
|
||||||
{
|
{
|
||||||
std::string saddr = std::string(it_param->base.saddr) + "_SG";
|
std::string saddr = std::string(it_param->base.saddr) + "_SG";
|
||||||
|
|
||||||
|
|
@ -149,7 +149,7 @@ LOCAL void param_load_active_sg_values(stru_LDevice &ld, int actSG)
|
||||||
LOG_E("param_num %d is not enough for saddr %s, actSG %d", it_param->param_num, saddr.c_str(), actSG);
|
LOG_E("param_num %d is not enough for saddr %s, actSG %d", it_param->param_num, saddr.c_str(), actSG);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
std::string val = mms_s_get_string_by_type(it_param->data[actSG-1], it_param->base.type);
|
std::string val = mms_s_get_string_by_type(it_param->p_data[actSG-1], it_param->base.type);
|
||||||
|
|
||||||
if(p_icd->ied.map_saddr_point.find(saddr) == p_icd->ied.map_saddr_point.end())
|
if(p_icd->ied.map_saddr_point.find(saddr) == p_icd->ied.map_saddr_point.end())
|
||||||
{
|
{
|
||||||
|
|
@ -203,7 +203,7 @@ LOCAL void param_load_edit_sg_values(stru_LDevice &ld, int editSG)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
for(std::vector<stru_mms_s_param>::iterator it_param = vec_params.begin(); it_param != vec_params.end(); it_param++)
|
for(std::vector<stru_mms_s_param>::iterator it_param = g_vec_params.begin(); it_param != g_vec_params.end(); it_param++)
|
||||||
{
|
{
|
||||||
std::string saddr = std::string(it_param->base.saddr) + "_SE";
|
std::string saddr = std::string(it_param->base.saddr) + "_SE";
|
||||||
|
|
||||||
|
|
@ -212,7 +212,7 @@ LOCAL void param_load_edit_sg_values(stru_LDevice &ld, int editSG)
|
||||||
LOG_E("param_num %d is not enough for saddr %s, editSG %d", it_param->param_num, saddr.c_str(), editSG);
|
LOG_E("param_num %d is not enough for saddr %s, editSG %d", it_param->param_num, saddr.c_str(), editSG);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
std::string val = mms_s_get_string_by_type(it_param->data[editSG-1], it_param->base.type);
|
std::string val = mms_s_get_string_by_type(it_param->p_data[editSG-1], it_param->base.type);
|
||||||
|
|
||||||
if(p_icd->ied.map_saddr_point.find(saddr) == p_icd->ied.map_saddr_point.end())
|
if(p_icd->ied.map_saddr_point.find(saddr) == p_icd->ied.map_saddr_point.end())
|
||||||
{
|
{
|
||||||
|
|
@ -627,7 +627,7 @@ LOCAL void edit_sg_confirmation_handler(void* parameter, SettingGroupControlBloc
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
for(std::vector<stru_mms_s_param>::iterator it_param = vec_params.begin(); it_param != vec_params.end(); it_param++)
|
for(std::vector<stru_mms_s_param>::iterator it_param = g_vec_params.begin(); it_param != g_vec_params.end(); it_param++)
|
||||||
{
|
{
|
||||||
std::string saddr_sg = std::string(it_param->base.saddr) + "_SG";
|
std::string saddr_sg = std::string(it_param->base.saddr) + "_SG";
|
||||||
std::string saddr_se = std::string(it_param->base.saddr) + "_SE";
|
std::string saddr_se = std::string(it_param->base.saddr) + "_SE";
|
||||||
|
|
@ -702,20 +702,20 @@ LOCAL MmsDataAccessError read_access_handler(LogicalDevice* ld, LogicalNode* ln,
|
||||||
/** 调试用:打印所有参数信息 */
|
/** 调试用:打印所有参数信息 */
|
||||||
LOCAL void param_values_show()
|
LOCAL void param_values_show()
|
||||||
{
|
{
|
||||||
if(vec_params.empty())
|
if(g_vec_params.empty())
|
||||||
{
|
{
|
||||||
LOG_E("vec_params is empty");
|
LOG_E("g_vec_params is empty");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
for(uint16_t i = 0; i < vec_params.size(); i++)
|
for(uint16_t i = 0; i < g_vec_params.size(); i++)
|
||||||
{
|
{
|
||||||
stru_mms_s_param ¶m = vec_params[i];
|
stru_mms_s_param ¶m = g_vec_params[i];
|
||||||
|
|
||||||
printf("saddr %s, desc %s, type %d\n", param.base.saddr, param.base.desc, param.base.type);
|
printf("saddr %s, desc %s, type %d\n", param.base.saddr, param.base.desc, param.base.type);
|
||||||
for(uint8_t j = 0; j < param.param_num; j++)
|
for(uint8_t j = 0; j < param.param_num; j++)
|
||||||
{
|
{
|
||||||
std::string val = mms_s_get_string_by_type(param.data[j], param.base.type);
|
std::string val = mms_s_get_string_by_type(param.p_data[j], param.base.type);
|
||||||
printf("index %d, val %s\n", j, val.c_str());
|
printf("index %d, val %s\n", j, val.c_str());
|
||||||
}
|
}
|
||||||
printf("\n");
|
printf("\n");
|
||||||
|
|
@ -737,12 +737,12 @@ int mms_s_param_register(stru_mms_s_param *p_param, uint16_t num, mms_s_param_cb
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
vec_params.clear();
|
g_vec_params.clear();
|
||||||
vec_params.reserve(num);
|
g_vec_params.reserve(num);
|
||||||
|
|
||||||
for(uint16_t i = 0; i < num; i++)
|
for(uint16_t i = 0; i < num; i++)
|
||||||
{
|
{
|
||||||
vec_params.push_back(p_param[i]);
|
g_vec_params.push_back(p_param[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(NULL != cb)
|
if(NULL != cb)
|
||||||
|
|
@ -764,9 +764,9 @@ int mms_s_param_register(stru_mms_s_param *p_param, uint16_t num, mms_s_param_cb
|
||||||
*/
|
*/
|
||||||
int param_init(IedServer server, stru_icd &icd)
|
int param_init(IedServer server, stru_icd &icd)
|
||||||
{
|
{
|
||||||
if(vec_params.empty())
|
if(g_vec_params.empty())
|
||||||
{
|
{
|
||||||
LOG_E("vec_params is empty");
|
LOG_E("g_vec_params is empty");
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -29,7 +29,7 @@
|
||||||
#include "mms_s_setting.h"
|
#include "mms_s_setting.h"
|
||||||
|
|
||||||
|
|
||||||
LOCAL std::vector<stru_mms_s_setting> vec_settings;
|
LOCAL std::vector<stru_mms_s_setting> g_vec_settings;
|
||||||
LOCAL mms_s_setting_cb cb_setting = NULL;
|
LOCAL mms_s_setting_cb cb_setting = NULL;
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -132,10 +132,10 @@ LOCAL int g_setting_update_funcs_count = sizeof(g_setting_update_funcs)/sizeof(g
|
||||||
*/
|
*/
|
||||||
LOCAL void setting_value_init(IedServer server, stru_icd &icd)
|
LOCAL void setting_value_init(IedServer server, stru_icd &icd)
|
||||||
{
|
{
|
||||||
for(std::vector<stru_mms_s_setting>::iterator it = vec_settings.begin(); it != vec_settings.end(); it++)
|
for(std::vector<stru_mms_s_setting>::iterator it = g_vec_settings.begin(); it != g_vec_settings.end(); it++)
|
||||||
{
|
{
|
||||||
std::string sAddr = it->base.saddr;
|
std::string sAddr = it->base.saddr;
|
||||||
std::string str = mms_s_get_string_by_type(it->data, it->base.type);
|
std::string str = mms_s_get_string_by_type(it->p_data, it->base.type);
|
||||||
|
|
||||||
if(icd.ied.map_saddr_point.find(sAddr) == icd.ied.map_saddr_point.end())
|
if(icd.ied.map_saddr_point.find(sAddr) == icd.ied.map_saddr_point.end())
|
||||||
{
|
{
|
||||||
|
|
@ -446,7 +446,7 @@ LOCAL MmsDataAccessError writeAccessHandler (DataAttribute* dataAttribute, MmsVa
|
||||||
LOG_I("da name: %s, sAddr: %s, fc %d", dataAttribute->name, dataAttribute->sAddr, dataAttribute->fc);
|
LOG_I("da name: %s, sAddr: %s, fc %d", dataAttribute->name, dataAttribute->sAddr, dataAttribute->fc);
|
||||||
}
|
}
|
||||||
|
|
||||||
for(std::vector<stru_mms_s_setting>::iterator it = vec_settings.begin(); it != vec_settings.end(); it++)
|
for(std::vector<stru_mms_s_setting>::iterator it = g_vec_settings.begin(); it != g_vec_settings.end(); it++)
|
||||||
{
|
{
|
||||||
std::string sAddr = it->base.saddr;
|
std::string sAddr = it->base.saddr;
|
||||||
|
|
||||||
|
|
@ -504,9 +504,9 @@ LOCAL MmsDataAccessError writeAccessHandler (DataAttribute* dataAttribute, MmsVa
|
||||||
*/
|
*/
|
||||||
LOCAL void setting_handle_init(IedServer server, stru_icd &icd)
|
LOCAL void setting_handle_init(IedServer server, stru_icd &icd)
|
||||||
{
|
{
|
||||||
for(int i = 0; i < vec_settings.size(); i++)
|
for(int i = 0; i < g_vec_settings.size(); i++)
|
||||||
{
|
{
|
||||||
std::string sAddr = vec_settings[i].base.saddr;
|
std::string sAddr = g_vec_settings[i].base.saddr;
|
||||||
|
|
||||||
if(icd.ied.map_saddr_point.find(sAddr) == icd.ied.map_saddr_point.end())
|
if(icd.ied.map_saddr_point.find(sAddr) == icd.ied.map_saddr_point.end())
|
||||||
{
|
{
|
||||||
|
|
@ -543,9 +543,9 @@ LOCAL void setting_handle_init(IedServer server, stru_icd &icd)
|
||||||
/** 调试用:打印已注册的定值信息 */
|
/** 调试用:打印已注册的定值信息 */
|
||||||
LOCAL void setting_values_show()
|
LOCAL void setting_values_show()
|
||||||
{
|
{
|
||||||
for(int i = 0; i < vec_settings.size(); i++)
|
for(int i = 0; i < g_vec_settings.size(); i++)
|
||||||
{
|
{
|
||||||
stru_mms_s_setting &setting = vec_settings[i];
|
stru_mms_s_setting &setting = g_vec_settings[i];
|
||||||
LOG_I("saddr %s, desc %s, type %d",
|
LOG_I("saddr %s, desc %s, type %d",
|
||||||
setting.base.saddr, setting.base.desc, setting.base.type);
|
setting.base.saddr, setting.base.desc, setting.base.type);
|
||||||
}
|
}
|
||||||
|
|
@ -566,12 +566,12 @@ int mms_s_setting_register(stru_mms_s_setting *p_setting, uint16_t num, mms_s_se
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
vec_settings.clear();
|
g_vec_settings.clear();
|
||||||
vec_settings.reserve(num);
|
g_vec_settings.reserve(num);
|
||||||
|
|
||||||
for(int i = 0; i < num; i++)
|
for(int i = 0; i < num; i++)
|
||||||
{
|
{
|
||||||
vec_settings.push_back(p_setting[i]);
|
g_vec_settings.push_back(p_setting[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(cb != NULL)
|
if(cb != NULL)
|
||||||
|
|
@ -595,9 +595,9 @@ int mms_s_setting_register(stru_mms_s_setting *p_setting, uint16_t num, mms_s_se
|
||||||
*/
|
*/
|
||||||
int setting_init(IedServer server, stru_icd &icd)
|
int setting_init(IedServer server, stru_icd &icd)
|
||||||
{
|
{
|
||||||
if(vec_settings.empty())
|
if(g_vec_settings.empty())
|
||||||
{
|
{
|
||||||
LOG_E("vec_settings is empty");
|
LOG_E("g_vec_settings is empty");
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -21,154 +21,152 @@
|
||||||
* - 找不到则默认为 0
|
* - 找不到则默认为 0
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include "myMms_s.h"
|
||||||
#include "mms_s_value.h"
|
#include "mms_s_value.h"
|
||||||
|
|
||||||
|
|
||||||
// ==================== 值更新回调(当前 Unused,预留给 mms_s_values_update) ====================
|
// ==================== 值更新回调(当前 Unused,预留给 mms_s_values_update) ====================
|
||||||
|
|
||||||
LOCAL void model_da_value_update_Boolean(IedServer server, DataAttribute *da, void *value);
|
LOCAL void model_da_value_update_Boolean(IedServer server, DataAttribute *da, std::string val);
|
||||||
LOCAL void model_da_value_update_INT32(IedServer server, DataAttribute *da, void *value);
|
LOCAL void model_da_value_update_INT32(IedServer server, DataAttribute *da, std::string val);
|
||||||
LOCAL void model_da_value_update_INT32U(IedServer server, DataAttribute *da, void *value);
|
LOCAL void model_da_value_update_INT32U(IedServer server, DataAttribute *da, std::string val);
|
||||||
LOCAL void model_da_value_update_FLOAT32(IedServer server, DataAttribute *da, void *value);
|
LOCAL void model_da_value_update_FLOAT32(IedServer server, DataAttribute *da, std::string val);
|
||||||
LOCAL void model_da_value_update_Enum(IedServer server, DataAttribute *da, void *value);
|
LOCAL void model_da_value_update_Enum(IedServer server, DataAttribute *da, std::string val);
|
||||||
LOCAL void model_da_value_update_Visible_String(IedServer server, DataAttribute *da, void *value);
|
LOCAL void model_da_value_update_Visible_String(IedServer server, DataAttribute *da, std::string val);
|
||||||
LOCAL void model_da_value_update_Unicode_String(IedServer server, DataAttribute *da, void *value);
|
LOCAL void model_da_value_update_Unicode_String(IedServer server, DataAttribute *da, std::string val);
|
||||||
LOCAL void model_da_value_update_timesramp(IedServer server, DataAttribute *da, void *value);
|
LOCAL void model_da_value_update_timesramp(IedServer server, DataAttribute *da, std::string val);
|
||||||
|
|
||||||
LOCAL struct
|
|
||||||
|
typedef void (*value_update_cb)(IedServer server, DataAttribute *da, std::string val);
|
||||||
|
LOCAL std::map<DataAttributeType, value_update_cb> g_iec61850s_value_update_cb_map =
|
||||||
{
|
{
|
||||||
const char *btype;
|
{IEC61850_BOOLEAN, model_da_value_update_Boolean},
|
||||||
void (*value_update_cb)(IedServer server, DataAttribute *da, void *value);
|
{IEC61850_INT8, NULL},
|
||||||
}g_iec61850s_value_update_cb[] =
|
{IEC61850_INT16, NULL},
|
||||||
{
|
{IEC61850_INT32, model_da_value_update_INT32},
|
||||||
{"BOOLEAN", model_da_value_update_Boolean},
|
{IEC61850_INT64, NULL},
|
||||||
{"INT8", NULL},
|
{IEC61850_INT128, NULL},
|
||||||
{"INT16", NULL},
|
{IEC61850_INT8U, NULL},
|
||||||
{"INT32", model_da_value_update_INT32},
|
{IEC61850_INT16U, NULL},
|
||||||
{"INT64", NULL},
|
{IEC61850_INT32U, model_da_value_update_INT32U},
|
||||||
{"INT128", NULL},
|
{IEC61850_FLOAT32, model_da_value_update_FLOAT32},
|
||||||
{"INT8U", NULL},
|
{IEC61850_FLOAT64, NULL},
|
||||||
{"INT16U", NULL},
|
{IEC61850_ENUMERATED, model_da_value_update_Enum},
|
||||||
{"INT32U", model_da_value_update_INT32U},
|
{IEC61850_OCTET_STRING_64, NULL},
|
||||||
{"FLOAT32", model_da_value_update_FLOAT32},
|
{IEC61850_OCTET_STRING_6, NULL},
|
||||||
{"FLOAT64", NULL},
|
{IEC61850_OCTET_STRING_8, NULL},
|
||||||
{"Enum", model_da_value_update_Enum},
|
{IEC61850_VISIBLE_STRING_32, model_da_value_update_Visible_String},
|
||||||
{"Octet64", NULL},
|
{IEC61850_VISIBLE_STRING_64, NULL},
|
||||||
{"Octet6", NULL},
|
{IEC61850_VISIBLE_STRING_65, NULL},
|
||||||
{"Octet8", NULL},
|
{IEC61850_VISIBLE_STRING_129, NULL},
|
||||||
{"VisString32", model_da_value_update_Visible_String},
|
{IEC61850_VISIBLE_STRING_255, NULL},
|
||||||
{"VisString64", model_da_value_update_Visible_String},
|
{IEC61850_UNICODE_STRING_255, model_da_value_update_Unicode_String},
|
||||||
{"VisString65", model_da_value_update_Visible_String},
|
{IEC61850_TIMESTAMP, model_da_value_update_timesramp},
|
||||||
{"VisString129", model_da_value_update_Visible_String},
|
{IEC61850_QUALITY, NULL},
|
||||||
{"VisString255", model_da_value_update_Visible_String},
|
{IEC61850_CHECK, NULL},
|
||||||
{"Unicode255", model_da_value_update_Unicode_String},
|
{IEC61850_CODEDENUM, NULL},
|
||||||
{"Timestamp", model_da_value_update_timesramp},
|
{IEC61850_GENERIC_BITSTRING, NULL},
|
||||||
{"Quality", NULL},
|
{IEC61850_CONSTRUCTED, NULL},
|
||||||
{"Check", NULL},
|
{IEC61850_ENTRY_TIME, NULL},
|
||||||
{"CodedEnum", NULL},
|
{IEC61850_PHYCOMADDR, NULL},
|
||||||
{"BitString", NULL},
|
{IEC61850_CURRENCY, NULL},
|
||||||
{"Struct", NULL},
|
{IEC61850_OPTFLDS, NULL},
|
||||||
{"EntryTime", NULL},
|
{IEC61850_TRGOPS, NULL},
|
||||||
{"PhyComAddr", NULL},
|
{IEC61850_DBPOS, NULL},
|
||||||
{"Currency", NULL},
|
|
||||||
{"OptFlds", NULL},
|
|
||||||
{"TrgOps", NULL},
|
|
||||||
{"Dbpos", NULL},
|
|
||||||
};
|
};
|
||||||
LOCAL int g_iec61850s_value_update_cb_count = sizeof(g_iec61850s_value_update_cb) / sizeof(g_iec61850s_value_update_cb[0]);
|
|
||||||
|
|
||||||
/** 更新 BOOLEAN 属性值(调用 IedServer_updateBooleanAttributeValue) */
|
/** 更新 BOOLEAN 属性值(调用 IedServer_updateBooleanAttributeValue) */
|
||||||
LOCAL void model_da_value_update_Boolean(IedServer server, DataAttribute *da, void *value)
|
LOCAL void model_da_value_update_Boolean(IedServer server, DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == server || NULL == da || NULL == value || strlen((char*)value) == 0)
|
if(NULL == server || NULL == da || "" == val)
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
int int_value = atoi((char*)value);
|
|
||||||
if(int_value == 0)
|
if(val == "false" || val == "0")
|
||||||
{
|
{
|
||||||
IedServer_updateBooleanAttributeValue(server, da, false);
|
IedServer_updateBooleanAttributeValue(server, da, false);
|
||||||
}
|
}
|
||||||
else if(int_value == 1)
|
else if(val == "true" || val == "1")
|
||||||
{
|
{
|
||||||
IedServer_updateBooleanAttributeValue(server, da, true);
|
IedServer_updateBooleanAttributeValue(server, da, true);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
LOG_E("Invalid boolean value %s", (char *)value);
|
LOG_E("Invalid boolean value %s", val.c_str());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/** 更新 INT32 属性值 */
|
/** 更新 INT32 属性值 */
|
||||||
LOCAL void model_da_value_update_INT32(IedServer server, DataAttribute *da, void *value)
|
LOCAL void model_da_value_update_INT32(IedServer server, DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == server || NULL == da || NULL == value || strlen((char*)value) == 0)
|
if(NULL == server || NULL == da || "" == val)
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
IedServer_updateInt32AttributeValue(server, da, atoi((char*)value));
|
IedServer_updateInt32AttributeValue(server, da, atoi(val.c_str()));
|
||||||
}
|
}
|
||||||
|
|
||||||
/** 更新 UINT32 属性值 */
|
/** 更新 UINT32 属性值 */
|
||||||
LOCAL void model_da_value_update_INT32U(IedServer server, DataAttribute *da, void *value)
|
LOCAL void model_da_value_update_INT32U(IedServer server, DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == server || NULL == da || NULL == value || strlen((char*)value) == 0)
|
if(NULL == server || NULL == da || "" == val)
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
IedServer_updateUnsignedAttributeValue(server, da, atoi((char*)value));
|
IedServer_updateUnsignedAttributeValue(server, da, atoi(val.c_str()));
|
||||||
}
|
}
|
||||||
|
|
||||||
/** 更新 FLOAT32 属性值 */
|
/** 更新 FLOAT32 属性值 */
|
||||||
LOCAL void model_da_value_update_FLOAT32(IedServer server, DataAttribute *da, void *value)
|
LOCAL void model_da_value_update_FLOAT32(IedServer server, DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == server || NULL == da || NULL == value || strlen((char*)value) == 0)
|
if(NULL == server || NULL == da || "" == val)
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
IedServer_updateFloatAttributeValue(server, da, atof((char*)value));
|
IedServer_updateFloatAttributeValue(server, da, atof(val.c_str()));
|
||||||
}
|
}
|
||||||
|
|
||||||
/** 更新 Enum 属性值(直接设置 mmsValue) */
|
/** 更新 Enum 属性值(直接设置 mmsValue) */
|
||||||
LOCAL void model_da_value_update_Enum(IedServer server, DataAttribute *da, void *value)
|
LOCAL void model_da_value_update_Enum(IedServer server, DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == server || NULL == da || NULL == value)
|
if(NULL == server || NULL == da || "" == val)
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
LOG_I("da %p, name %s, value %d", da, da->name, *(int *)value);
|
LOG_I("da %p, name %s, value %d", da, da->name, atoi(val.c_str()));
|
||||||
da->mmsValue = MmsValue_newIntegerFromInt32(*(int *)value);
|
da->mmsValue = MmsValue_newIntegerFromInt32(atoi(val.c_str()));
|
||||||
}
|
}
|
||||||
|
|
||||||
/** 更新 VisibleString 属性值 */
|
/** 更新 VisibleString 属性值 */
|
||||||
LOCAL void model_da_value_update_Visible_String(IedServer server, DataAttribute *da, void *value)
|
LOCAL void model_da_value_update_Visible_String(IedServer server, DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == server || NULL == da || NULL == value || strlen((char*)value) == 0)
|
if(NULL == server || NULL == da || "" == val)
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
IedServer_updateVisibleStringAttributeValue(server, da, (char*)value);
|
IedServer_updateVisibleStringAttributeValue(server, da, (char*)val.c_str());
|
||||||
}
|
}
|
||||||
|
|
||||||
/** 更新 Unicode String 属性值 */
|
/** 更新 Unicode String 属性值 */
|
||||||
LOCAL void model_da_value_update_Unicode_String(IedServer server, DataAttribute *da, void *value)
|
LOCAL void model_da_value_update_Unicode_String(IedServer server, DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == server || NULL == da || NULL == value || strlen((char*)value) == 0)
|
if(NULL == server || NULL == da || "" == val)
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
IedServer_updateAttributeValue(server, da, MmsValue_newMmsString((char*)value));
|
IedServer_updateAttributeValue(server, da, MmsValue_newMmsString((char*)val.c_str()));
|
||||||
}
|
}
|
||||||
|
|
||||||
/** 更新 Timestamp 属性值(设为当前毫秒时间) */
|
/** 更新 Timestamp 属性值(设为当前毫秒时间) */
|
||||||
LOCAL void model_da_value_update_timesramp(IedServer server, DataAttribute *da, void *value)
|
LOCAL void model_da_value_update_timesramp(IedServer server, DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == server || NULL == da)
|
if(NULL == server || NULL == da)
|
||||||
{
|
{
|
||||||
|
|
@ -182,14 +180,14 @@ LOCAL void model_da_value_update_timesramp(IedServer server, DataAttribute *da,
|
||||||
|
|
||||||
// ==================== 值初始化回调(mms_s_values_init 使用) ====================
|
// ==================== 值初始化回调(mms_s_values_init 使用) ====================
|
||||||
|
|
||||||
LOCAL void mms_s_da_value_init_BOOLEAN(DataAttribute *da, void *value);
|
LOCAL void mms_s_da_value_init_BOOLEAN(DataAttribute *da, std::string val);
|
||||||
LOCAL void mms_s_da_value_init_INT32(DataAttribute *da, void *value);
|
LOCAL void mms_s_da_value_init_INT32(DataAttribute *da, std::string val);
|
||||||
LOCAL void mms_s_da_value_init_INT32U(DataAttribute *da, void *value);
|
LOCAL void mms_s_da_value_init_INT32U(DataAttribute *da, std::string val);
|
||||||
LOCAL void mms_s_da_value_init_FLOAT32(DataAttribute *da, void *value);
|
LOCAL void mms_s_da_value_init_FLOAT32(DataAttribute *da, std::string val);
|
||||||
LOCAL void mms_s_da_value_init_Visible_String(DataAttribute *da, void *value);
|
LOCAL void mms_s_da_value_init_Visible_String(DataAttribute *da, std::string val);
|
||||||
LOCAL void mms_s_da_value_init_Unicode_String(DataAttribute *da, void *value);
|
LOCAL void mms_s_da_value_init_Unicode_String(DataAttribute *da, std::string val);
|
||||||
LOCAL void mms_s_da_value_init_Timestamp(DataAttribute *da, void *value);
|
LOCAL void mms_s_da_value_init_Timestamp(DataAttribute *da, std::string val);
|
||||||
LOCAL void mms_s_da_value_init_Dbpos(DataAttribute *da, void *value);
|
LOCAL void mms_s_da_value_init_Dbpos(DataAttribute *da, std::string val);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* bType 到 DA 初始化函数的分发表
|
* bType 到 DA 初始化函数的分发表
|
||||||
|
|
@ -197,11 +195,10 @@ LOCAL void mms_s_da_value_init_Dbpos(DataAttribute *da, void *value);
|
||||||
* 每个 bType 字符串对应一个初始化函数,用于将字符串值转换为 MmsValue 并设置到 DA。
|
* 每个 bType 字符串对应一个初始化函数,用于将字符串值转换为 MmsValue 并设置到 DA。
|
||||||
* NULL 表示该类型暂不需要显式初始化(libiec61850 有默认行为)。
|
* NULL 表示该类型暂不需要显式初始化(libiec61850 有默认行为)。
|
||||||
*/
|
*/
|
||||||
LOCAL struct
|
|
||||||
{
|
typedef void (*value_init_cb)(DataAttribute *da, std::string val);
|
||||||
const char *bType;
|
|
||||||
void (*value_init)(DataAttribute *da, void *value);
|
LOCAL std::map<std::string, value_init_cb> g_iec61850s_value_init_cb_map =
|
||||||
}g_iec61850s_value_init_cb[] =
|
|
||||||
{
|
{
|
||||||
{"BOOLEAN", mms_s_da_value_init_BOOLEAN},
|
{"BOOLEAN", mms_s_da_value_init_BOOLEAN},
|
||||||
{"INT8", NULL},
|
{"INT8", NULL},
|
||||||
|
|
@ -238,129 +235,127 @@ LOCAL struct
|
||||||
{"Dbpos", mms_s_da_value_init_Dbpos},
|
{"Dbpos", mms_s_da_value_init_Dbpos},
|
||||||
};
|
};
|
||||||
|
|
||||||
LOCAL int g_iec61850s_value_init_cb_count = sizeof(g_iec61850s_value_init_cb) / sizeof(g_iec61850s_value_init_cb[0]);
|
|
||||||
|
|
||||||
/** 初始化 BOOLEAN:根据 val 字符串 "true"/"1" 创建 MmsValue */
|
/** 初始化 BOOLEAN:根据 val 字符串 "true"/"1" 创建 MmsValue */
|
||||||
LOCAL void mms_s_da_value_init_BOOLEAN(DataAttribute *da, void *value)
|
LOCAL void mms_s_da_value_init_BOOLEAN(DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == da)
|
if(NULL == da || val.empty())
|
||||||
{
|
{
|
||||||
LOG_E("da is NULL");
|
LOG_E("da or val is empty, da %p, val %s", da, val.c_str());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(value == NULL || strlen((char*)value) == 0 || strcmp((char*)value, "false") == 0 || strcmp((char*)value, "0") == 0)
|
if(val == "false" || val == "0")
|
||||||
{
|
{
|
||||||
da->mmsValue = MmsValue_newBoolean(false);
|
da->mmsValue = MmsValue_newBoolean(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(value != NULL && (strcmp((char*)value, "true") == 0 || strcmp((char*)value, "1") == 0))
|
if(val == "true" || val == "1")
|
||||||
{
|
{
|
||||||
da->mmsValue = MmsValue_newBoolean(true);
|
da->mmsValue = MmsValue_newBoolean(true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/** 初始化 INT32:根据 val 字符串创建 MmsValue */
|
/** 初始化 INT32:根据 val 字符串创建 MmsValue */
|
||||||
LOCAL void mms_s_da_value_init_INT32(DataAttribute *da, void *value)
|
LOCAL void mms_s_da_value_init_INT32(DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == da)
|
if(NULL == da || val.empty())
|
||||||
{
|
{
|
||||||
LOG_E("da is NULL");
|
LOG_E("da or val is empty, da %p, val %s", da, val.c_str());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(value == NULL || strlen((char*)value) == 0)
|
if(val == "")
|
||||||
{
|
{
|
||||||
da->mmsValue = MmsValue_newIntegerFromInt32(0);
|
da->mmsValue = MmsValue_newIntegerFromInt32(0);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
da->mmsValue = MmsValue_newIntegerFromInt32(atoi((char*)value));
|
da->mmsValue = MmsValue_newIntegerFromInt32(atoi(val.c_str()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/** 初始化 UINT32:根据 val 字符串创建 MmsValue */
|
/** 初始化 UINT32:根据 val 字符串创建 MmsValue */
|
||||||
LOCAL void mms_s_da_value_init_INT32U(DataAttribute *da, void *value)
|
LOCAL void mms_s_da_value_init_INT32U(DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == da)
|
if(NULL == da || val.empty())
|
||||||
{
|
{
|
||||||
LOG_E("da is NULL");
|
LOG_E("da or val is empty, da %p, val %s", da, val.c_str());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(value == NULL || strlen((char*)value) == 0)
|
if(val == "")
|
||||||
{
|
{
|
||||||
da->mmsValue = MmsValue_newUnsignedFromUint32(0);
|
da->mmsValue = MmsValue_newUnsignedFromUint32(0);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
da->mmsValue = MmsValue_newUnsignedFromUint32(atoi((char*)value));
|
da->mmsValue = MmsValue_newUnsignedFromUint32(atoi(val.c_str()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/** 初始化 FLOAT32:根据 val 字符串创建 MmsValue */
|
/** 初始化 FLOAT32:根据 val 字符串创建 MmsValue */
|
||||||
LOCAL void mms_s_da_value_init_FLOAT32(DataAttribute *da, void *value)
|
LOCAL void mms_s_da_value_init_FLOAT32(DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == da)
|
if(NULL == da || val.empty())
|
||||||
{
|
{
|
||||||
LOG_E("da is NULL");
|
LOG_E("da or val is empty, da %p, val %s", da, val.c_str());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(value == NULL || strlen((char*)value) == 0)
|
if(val == "")
|
||||||
{
|
{
|
||||||
da->mmsValue = MmsValue_newFloat(0.0);
|
da->mmsValue = MmsValue_newFloat(0.0);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
da->mmsValue = MmsValue_newFloat(atof((char*)value));
|
da->mmsValue = MmsValue_newFloat(atof(val.c_str()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/** 初始化 VisibleString:根据 val 字符串创建 MmsValue */
|
/** 初始化 VisibleString:根据 val 字符串创建 MmsValue */
|
||||||
LOCAL void mms_s_da_value_init_Visible_String(DataAttribute *da, void *value)
|
LOCAL void mms_s_da_value_init_Visible_String(DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == da)
|
if(NULL == da || val.empty())
|
||||||
{
|
{
|
||||||
LOG_E("da is NULL");
|
LOG_E("da or val is empty, da %p, val %s", da, val.c_str());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(value == NULL || strlen((char*)value) == 0)
|
if(val == "")
|
||||||
{
|
{
|
||||||
da->mmsValue = MmsValue_newVisibleString("");
|
da->mmsValue = MmsValue_newVisibleString("");
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
da->mmsValue = MmsValue_newVisibleString((char*)value);
|
da->mmsValue = MmsValue_newVisibleString(val.c_str());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/** 初始化 Unicode String:根据 val 字符串创建 MmsValue */
|
/** 初始化 Unicode String:根据 val 字符串创建 MmsValue */
|
||||||
LOCAL void mms_s_da_value_init_Unicode_String(DataAttribute *da, void *value)
|
LOCAL void mms_s_da_value_init_Unicode_String(DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == da)
|
if(NULL == da || val.empty())
|
||||||
{
|
{
|
||||||
LOG_E("da is NULL");
|
LOG_E("da or val is empty, da %p, val %s", da, val.c_str());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(value == NULL || strlen((char*)value) == 0)
|
if(val == "")
|
||||||
{
|
{
|
||||||
da->mmsValue = MmsValue_newMmsString("");
|
da->mmsValue = MmsValue_newMmsString("");
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
da->mmsValue = MmsValue_newMmsString((char*)value);
|
da->mmsValue = MmsValue_newMmsString(val.c_str());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/** 初始化 Timestamp:设为当前毫秒时间 */
|
/** 初始化 Timestamp:设为当前毫秒时间 */
|
||||||
LOCAL void mms_s_da_value_init_Timestamp(DataAttribute *da, void *value)
|
LOCAL void mms_s_da_value_init_Timestamp(DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == da)
|
if(NULL == da || val.empty())
|
||||||
{
|
{
|
||||||
LOG_E("da is NULL");
|
LOG_E("da or val is empty, da %p, val %s", da, val.c_str());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -371,23 +366,23 @@ LOCAL void mms_s_da_value_init_Timestamp(DataAttribute *da, void *value)
|
||||||
* 初始化 Dbpos(双点位置):
|
* 初始化 Dbpos(双点位置):
|
||||||
* val=0 → INTERMEDIATE_STATE, 1 → OFF, 2 → ON, 3/其他 → BAD_STATE
|
* val=0 → INTERMEDIATE_STATE, 1 → OFF, 2 → ON, 3/其他 → BAD_STATE
|
||||||
*/
|
*/
|
||||||
LOCAL void mms_s_da_value_init_Dbpos(DataAttribute *da, void *value)
|
LOCAL void mms_s_da_value_init_Dbpos(DataAttribute *da, std::string val)
|
||||||
{
|
{
|
||||||
if(NULL == da)
|
if(NULL == da || val.empty())
|
||||||
{
|
{
|
||||||
LOG_E("da is NULL");
|
LOG_E("da or val is empty, da %p, val %s", da, val.c_str());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
Dbpos pos = DBPOS_INTERMEDIATE_STATE;
|
Dbpos pos = DBPOS_INTERMEDIATE_STATE;
|
||||||
|
|
||||||
if(value == NULL || strlen((char*)value) == 0)
|
if(val == "")
|
||||||
{
|
{
|
||||||
pos = DBPOS_INTERMEDIATE_STATE;
|
pos = DBPOS_INTERMEDIATE_STATE;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
int i = atoi((char*)value);
|
int i = atoi(val.c_str());
|
||||||
if(i == 0)
|
if(i == 0)
|
||||||
{
|
{
|
||||||
pos = DBPOS_INTERMEDIATE_STATE;
|
pos = DBPOS_INTERMEDIATE_STATE;
|
||||||
|
|
@ -414,7 +409,7 @@ LOCAL void mms_s_da_value_init_Dbpos(DataAttribute *da, void *value)
|
||||||
|
|
||||||
if(mms_s_dbg_get())
|
if(mms_s_dbg_get())
|
||||||
{
|
{
|
||||||
LOG_I("da %s-%s, value %s, pos %d", da->parent->name, da->name, (char *)value, pos);
|
LOG_I("da %s-%s, value %s, pos %d", da->parent->name, da->name, val.c_str(), pos);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -476,22 +471,16 @@ LOCAL void mms_s_da_values_init(stru_icd &icd, std::string da_name, stru_all_DA
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
for(int i = 0; i < g_iec61850s_value_init_cb_count; i++)
|
if(g_iec61850s_value_init_cb_map.find(p_all_da->bType) == g_iec61850s_value_init_cb_map.end())
|
||||||
{
|
{
|
||||||
if(p_all_da->bType.compare(g_iec61850s_value_init_cb[i].bType) == 0)
|
LOG_E("BDAType %s not found in ICD", p_all_da->bType.c_str());
|
||||||
{
|
return;
|
||||||
if(NULL != g_iec61850s_value_init_cb[i].value_init)
|
|
||||||
{
|
|
||||||
g_iec61850s_value_init_cb[i].value_init(p_all_da->DA, (void *)p_all_da->val.c_str());
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
LOG_E("BDAType %s not found in ICD", p_all_da->bType.c_str());
|
if(NULL != g_iec61850s_value_init_cb_map[p_all_da->bType])
|
||||||
|
{
|
||||||
|
g_iec61850s_value_init_cb_map[p_all_da->bType](p_all_da->DA, p_all_da->val);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -546,4 +535,66 @@ void mms_s_values_init()
|
||||||
mms_s_do_values_init(*p_icd, it_ln->map_all_do);
|
mms_s_do_values_init(*p_icd, it_ln->map_all_do);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
LOCAL void mms_s_value_update(const char *str_saddr, const char *str_val)
|
||||||
|
{
|
||||||
|
if(NULL == str_saddr || NULL == str_val)
|
||||||
|
{
|
||||||
|
LOG_E("str_saddr or str_val is NULL, str_saddr %p, str_val %p", str_saddr, str_val);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string saddr = str_saddr;
|
||||||
|
std::string val = str_val;
|
||||||
|
|
||||||
|
stru_icd *p_icd = mms_s_get_icd_ptr();
|
||||||
|
if(NULL == p_icd)
|
||||||
|
{
|
||||||
|
LOG_E("p_icd is NULL");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::map<std::string, stru_saddr_point> map_saddr_point = p_icd->ied.map_saddr_point;
|
||||||
|
|
||||||
|
if(map_saddr_point.find(saddr) == map_saddr_point.end())
|
||||||
|
{
|
||||||
|
LOG_E("sAddr %s not found in ICD", saddr.c_str());
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
stru_saddr_point &saddr_point = map_saddr_point[saddr];
|
||||||
|
|
||||||
|
ModelNode *p_node = saddr_point.node;
|
||||||
|
if(NULL == p_node)
|
||||||
|
{
|
||||||
|
LOG_E("p_node is NULL");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(p_node->modelType != DataAttributeModelType)
|
||||||
|
{
|
||||||
|
LOG_E("p_node is not a DataAttribute");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
DataAttribute *p_da = (DataAttribute *)p_node;
|
||||||
|
|
||||||
|
if(g_iec61850s_value_update_cb_map.find(p_da->type) == g_iec61850s_value_update_cb_map.end())
|
||||||
|
{
|
||||||
|
LOG_E("EnumType %d not found in ICD", p_da->type);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
IedServer p_ied_server = mms_s_get_ied_server_ptr();
|
||||||
|
|
||||||
|
if(NULL != g_iec61850s_value_update_cb_map[p_da->type] && p_ied_server != NULL)
|
||||||
|
{
|
||||||
|
g_iec61850s_value_update_cb_map[p_da->type](p_ied_server, p_da, val);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void mms_s_value_update_register(mms_s_value_update_cb *cb)
|
||||||
|
{
|
||||||
|
(*cb) = mms_s_value_update;
|
||||||
}
|
}
|
||||||
|
|
@ -1,6 +1,7 @@
|
||||||
#include <mutex>
|
#include <mutex>
|
||||||
#include <queue>
|
#include <queue>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
#include <sys/time.h>
|
||||||
|
|
||||||
#include "dc_event.h"
|
#include "dc_event.h"
|
||||||
#include "myLog.h"
|
#include "myLog.h"
|
||||||
|
|
@ -20,6 +21,15 @@ LOCAL std::queue<stru_dc_fault> g_fault_queue;
|
||||||
LOCAL std::vector<dc_queue_pop_cb> g_fault_queue_pop_cbs;
|
LOCAL std::vector<dc_queue_pop_cb> g_fault_queue_pop_cbs;
|
||||||
|
|
||||||
|
|
||||||
|
LOCAL void dc_get_unix_time(uint32_t &sec, uint16_t &ms)
|
||||||
|
{
|
||||||
|
struct timeval tv;
|
||||||
|
gettimeofday(&tv, nullptr);
|
||||||
|
sec = tv.tv_sec;
|
||||||
|
ms = tv.tv_usec / 1000;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
int dc_disturb_dd_register_queue_pop(dc_queue_pop_cb cb)
|
int dc_disturb_dd_register_queue_pop(dc_queue_pop_cb cb)
|
||||||
{
|
{
|
||||||
if(!cb)
|
if(!cb)
|
||||||
|
|
@ -35,8 +45,15 @@ int dc_disturb_dd_register_queue_pop(dc_queue_pop_cb cb)
|
||||||
|
|
||||||
int dc_disturb_dd_queue_push(const stru_disturb_dd &dd)
|
int dc_disturb_dd_queue_push(const stru_disturb_dd &dd)
|
||||||
{
|
{
|
||||||
|
stru_disturb_dd local_dd = dd;
|
||||||
|
if(dd.sec == 0 && dd.ms == 0)
|
||||||
|
{
|
||||||
|
dc_get_unix_time(local_dd.sec, local_dd.ms);
|
||||||
|
}
|
||||||
|
|
||||||
std::lock_guard<std::mutex> lock(g_disturb_dd_mutex);
|
std::lock_guard<std::mutex> lock(g_disturb_dd_mutex);
|
||||||
g_disturb_dd_queue.push(dd);
|
|
||||||
|
g_disturb_dd_queue.push(local_dd);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -77,8 +94,14 @@ int dc_event_register_queue_pop(dc_queue_pop_cb cb)
|
||||||
|
|
||||||
int dc_event_queue_push(const stru_dc_soe &soe)
|
int dc_event_queue_push(const stru_dc_soe &soe)
|
||||||
{
|
{
|
||||||
|
stru_dc_soe local_soe = soe;
|
||||||
|
if(soe.sec == 0 && soe.ms == 0)
|
||||||
|
{
|
||||||
|
dc_get_unix_time(local_soe.sec, local_soe.ms);
|
||||||
|
}
|
||||||
|
|
||||||
std::lock_guard<std::mutex> lock(g_soe_mutex);
|
std::lock_guard<std::mutex> lock(g_soe_mutex);
|
||||||
g_soe_queue.push(soe);
|
g_soe_queue.push(local_soe);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -119,8 +142,21 @@ int dc_fault_register_queue_pop(dc_queue_pop_cb cb)
|
||||||
|
|
||||||
int dc_fault_queue_push(const stru_dc_fault &fault)
|
int dc_fault_queue_push(const stru_dc_fault &fault)
|
||||||
{
|
{
|
||||||
|
stru_dc_fault local_fault = fault;
|
||||||
|
if(local_fault.vec_soe.empty())
|
||||||
|
{
|
||||||
|
LOG_E("dc_fault_queue_push: vec_soe is empty");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
stru_dc_soe &soe = local_fault.vec_soe[0];
|
||||||
|
if(soe.sec == 0 && soe.ms == 0)
|
||||||
|
{
|
||||||
|
dc_get_unix_time(soe.sec, soe.ms);
|
||||||
|
}
|
||||||
|
|
||||||
std::lock_guard<std::mutex> lock(g_fault_mutex);
|
std::lock_guard<std::mutex> lock(g_fault_mutex);
|
||||||
g_fault_queue.push(fault);
|
g_fault_queue.push(local_fault);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -132,8 +132,8 @@ LOCAL void iec_event_queue_callback(void *p_data)
|
||||||
if(iec_cfg_ptr_get()->vec_st[i].link.compare(soe.saddr) == 0)
|
if(iec_cfg_ptr_get()->vec_st[i].link.compare(soe.saddr) == 0)
|
||||||
{
|
{
|
||||||
LOG_I("iec_event_queue_callback: found saddr %s in vec_st, set status %d, sec %d, ums %d",
|
LOG_I("iec_event_queue_callback: found saddr %s in vec_st, set status %d, sec %d, ums %d",
|
||||||
soe.saddr.c_str(), soe.status, soe.sec, soe.ums);
|
soe.saddr.c_str(), soe.status, soe.sec, soe.ms);
|
||||||
UserWriteSoeEvent(i, soe.status, soe.sec, soe.ums);
|
UserWriteSoeEvent(i, soe.status, soe.sec, soe.ms);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -167,7 +167,7 @@ LOCAL void iec_fault_queue_callback(void *p_data)
|
||||||
soe_info.uiInfoAddr = i;
|
soe_info.uiInfoAddr = i;
|
||||||
soe_info.ucStatus = fault.vec_soe[0].status;
|
soe_info.ucStatus = fault.vec_soe[0].status;
|
||||||
soe_info.uiSeconds = fault.vec_soe[0].sec;
|
soe_info.uiSeconds = fault.vec_soe[0].sec;
|
||||||
soe_info.usMs = fault.vec_soe[0].ums;
|
soe_info.usMs = fault.vec_soe[0].ms;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -7,7 +7,7 @@
|
||||||
|
|
||||||
LOCAL void mms_event_back(void *arg, int ret);
|
LOCAL void mms_event_back(void *arg, int ret);
|
||||||
|
|
||||||
LOCAL const char *g_61850m_prj_path = "/mnt/RTU/test/file/MMS/";
|
LOCAL const char *g_61850m_prj_path = "/mnt/RTU/test/config/MMS/";
|
||||||
|
|
||||||
typedef struct
|
typedef struct
|
||||||
{
|
{
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,28 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
#include <vector>
|
||||||
|
#include <map>
|
||||||
|
|
||||||
|
|
||||||
|
#include "myBase.h"
|
||||||
|
#include "myMms_s.h"
|
||||||
|
#include "tinyxml2.h"
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
typedef struct
|
||||||
|
{
|
||||||
|
std::vector<stru_mms_s_signal_base> vec_st;
|
||||||
|
std::vector<stru_mms_s_signal_base> vec_mx;
|
||||||
|
std::vector<stru_mms_s_signal_base> vec_co;
|
||||||
|
std::vector<stru_mms_s_signal_base> vec_ao;
|
||||||
|
std::vector<stru_mms_s_signal_base> vec_param;
|
||||||
|
}stru_mms_cfg;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
int parse_mms_xml(const std::string &path);
|
||||||
|
void show_mms_xml(stru_mms_cfg &cfg);
|
||||||
|
|
||||||
|
stru_mms_cfg *mms_cfg_ptr_get(void);
|
||||||
|
|
@ -3,36 +3,96 @@
|
||||||
#include "myLog.h"
|
#include "myLog.h"
|
||||||
#include "myCmd.h"
|
#include "myCmd.h"
|
||||||
#include "myDatacenter.h"
|
#include "myDatacenter.h"
|
||||||
|
#include "parse_xml.h"
|
||||||
|
|
||||||
LOCAL std::vector<stru_mms_s_control> vec_control =
|
typedef struct
|
||||||
{
|
{
|
||||||
{"iec61850m.prj.co.0", "遥控01", 4},
|
stru_mms_s_signal_base base;
|
||||||
{"iec61850m.prj.co.1", "遥控02", 4},
|
void *p_data;
|
||||||
{"iec61850m.prj.co.2", "遥控03", 4},
|
}stru_local_st_mx;
|
||||||
{"iec61850m.prj.co.3", "遥控04", 4},
|
|
||||||
};
|
|
||||||
|
|
||||||
LOCAL std::vector<stru_mms_s_setting> vec_setting =
|
LOCAL std::vector<stru_local_st_mx> g_vec_st = {};
|
||||||
|
LOCAL std::vector<stru_local_st_mx> g_vec_mx = {};
|
||||||
|
LOCAL std::vector<stru_mms_s_control> g_vec_control = {};
|
||||||
|
LOCAL std::vector<stru_mms_s_setting> g_vec_setting = {};
|
||||||
|
LOCAL std::vector<stru_mms_s_param> g_vec_param = {};
|
||||||
|
LOCAL mms_s_value_update_cb g_mms_s_value_update_cb = NULL;
|
||||||
|
|
||||||
|
|
||||||
|
LOCAL void iec61850s_st_mx_change_callback(std::string saddr, uint8_t data_type, void *p_data, void *p_last_data)
|
||||||
{
|
{
|
||||||
|
if(NULL == p_data || NULL == p_last_data)
|
||||||
{
|
{
|
||||||
.base = {.saddr = "iec61850m.prj.ao.0", .desc = "参数01", .type = DATA_TYPE_S32},
|
LOG_E("p_data or p_last_data is NULL");
|
||||||
.data = NULL,
|
return;
|
||||||
},
|
|
||||||
{
|
|
||||||
.base = {.saddr = "iec61850m.prj.ao.1", .desc = "参数02", .type = DATA_TYPE_STR},
|
|
||||||
.data = NULL,
|
|
||||||
}
|
}
|
||||||
};
|
|
||||||
|
|
||||||
LOCAL std::vector<stru_mms_s_param> vec_param =
|
std::string val = dc_get_signal_val(p_data, data_type);
|
||||||
{
|
if(val.empty())
|
||||||
{
|
{
|
||||||
.base = {.saddr = "iec61850m.prj.param.0", .desc = "定值01", .type = DATA_TYPE_F32},
|
LOG_E("val is empty");
|
||||||
.data = NULL,
|
return;
|
||||||
},
|
}
|
||||||
};
|
|
||||||
|
|
||||||
void iec61850s_control_callback(stru_mms_s_control *p_control, uint8_t state)
|
LOG_I("st mx change callback saddr: %s, val: %s", saddr.c_str(), val.c_str());
|
||||||
|
if(g_mms_s_value_update_cb != NULL)
|
||||||
|
{
|
||||||
|
g_mms_s_value_update_cb(saddr.c_str(), val.c_str());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
LOCAL int iec61850s_st_signals_init(std::vector<stru_mms_s_signal_base> &vec_st)
|
||||||
|
{
|
||||||
|
LOG_I("st signals init, vec_st size: %i", vec_st.size());
|
||||||
|
|
||||||
|
g_vec_st.clear();
|
||||||
|
g_vec_st.reserve(vec_st.capacity());
|
||||||
|
|
||||||
|
for(auto &it : vec_st)
|
||||||
|
{
|
||||||
|
stru_local_st_mx st = {};
|
||||||
|
st.base = it;
|
||||||
|
std::string desc = "";
|
||||||
|
|
||||||
|
if(0 != dc_signal_out_link_with_callback(st.base.saddr, &st.p_data, iec61850s_st_mx_change_callback))
|
||||||
|
{
|
||||||
|
LOG_E("dc_signal_out_link_with_callback failed");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
g_vec_st.push_back(st);
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
LOCAL int iec61850s_mx_signals_init(std::vector<stru_mms_s_signal_base> &vec_mx)
|
||||||
|
{
|
||||||
|
LOG_I("mx signals init, vec_mx size: %i", vec_mx.size());
|
||||||
|
|
||||||
|
g_vec_mx.clear();
|
||||||
|
g_vec_mx.reserve(vec_mx.capacity());
|
||||||
|
|
||||||
|
for(auto &it : vec_mx)
|
||||||
|
{
|
||||||
|
stru_local_st_mx mx = {};
|
||||||
|
mx.base = it;
|
||||||
|
std::string desc = "";
|
||||||
|
|
||||||
|
if(0 != dc_signal_out_link_with_callback(mx.base.saddr, &mx.p_data, iec61850s_st_mx_change_callback))
|
||||||
|
{
|
||||||
|
LOG_E("dc_signal_out_link_with_callback failed");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
g_vec_mx.push_back(mx);
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
LOCAL void iec61850s_control_callback(stru_mms_s_control *p_control, uint8_t state)
|
||||||
{
|
{
|
||||||
if(NULL == p_control)
|
if(NULL == p_control)
|
||||||
{
|
{
|
||||||
|
|
@ -40,7 +100,9 @@ void iec61850s_control_callback(stru_mms_s_control *p_control, uint8_t state)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
LOG_I("control callback called saddr: %s, state: %i", p_control->saddr, state);
|
stru_mms_s_signal_base &base = p_control->base;
|
||||||
|
|
||||||
|
LOG_I("control callback called saddr: %s, state: %i", base.saddr, state);
|
||||||
|
|
||||||
uint8_t temp_st = 0;
|
uint8_t temp_st = 0;
|
||||||
stru_signal_ctrl ctrl = {
|
stru_signal_ctrl ctrl = {
|
||||||
|
|
@ -50,38 +112,67 @@ void iec61850s_control_callback(stru_mms_s_control *p_control, uint8_t state)
|
||||||
.p_data = &temp_st,
|
.p_data = &temp_st,
|
||||||
};
|
};
|
||||||
|
|
||||||
if(p_control->ctrl_model == CONTROL_MODEL_DIRECT_NORMAL || p_control->ctrl_model == CONTROL_MODEL_DIRECT_ENHANCED)
|
if(base.ctrl_model == CONTROL_MODEL_DIRECT_NORMAL || base.ctrl_model == CONTROL_MODEL_DIRECT_ENHANCED)
|
||||||
{
|
{
|
||||||
ctrl.type = SIGNAL_CTRL_TYPE::DIRECT_NORMAL;
|
ctrl.type = SIGNAL_CTRL_TYPE::DIRECT_NORMAL;
|
||||||
if(0 != dc_signal_yk_set_status(p_control->saddr, SIGNAL_CTRL_STEP::DIRECT, ctrl, &state))
|
if(0 != dc_signal_yk_set_status(base.saddr, SIGNAL_CTRL_STEP::DIRECT, ctrl, &state))
|
||||||
{
|
{
|
||||||
MY_LOG_E("dc_signal_yk_set_status failed");
|
MY_LOG_E("dc_signal_yk_set_status failed");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if(p_control->ctrl_model == CONTROL_MODEL_SBO_NORMAL || p_control->ctrl_model == CONTROL_MODEL_SBO_ENHANCED)
|
else if(base.ctrl_model == CONTROL_MODEL_SBO_NORMAL || base.ctrl_model == CONTROL_MODEL_SBO_ENHANCED)
|
||||||
{
|
{
|
||||||
ctrl.type = SIGNAL_CTRL_TYPE::SBO_NORMAL;
|
ctrl.type = SIGNAL_CTRL_TYPE::SBO_NORMAL;
|
||||||
if(0 != dc_signal_yk_set_status(p_control->saddr, SIGNAL_CTRL_STEP::SELECT, ctrl, &state))
|
if(0 != dc_signal_yk_set_status(base.saddr, SIGNAL_CTRL_STEP::SELECT, ctrl, &state))
|
||||||
{
|
{
|
||||||
MY_LOG_E("dc_signal_yk_set_status failed");
|
MY_LOG_E("dc_signal_yk_set_status failed");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(0 != dc_signal_yk_set_status(p_control->saddr, SIGNAL_CTRL_STEP::DIRECT, ctrl, &state))
|
if(0 != dc_signal_yk_set_status(base.saddr, SIGNAL_CTRL_STEP::DIRECT, ctrl, &state))
|
||||||
{
|
{
|
||||||
MY_LOG_E("dc_signal_yk_set_status failed");
|
MY_LOG_E("dc_signal_yk_set_status failed");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if(p_control->ctrl_model == CONTROL_MODEL_STATUS_ONLY)
|
else if(base.ctrl_model == CONTROL_MODEL_STATUS_ONLY)
|
||||||
{
|
{
|
||||||
MY_LOG_I("CONTROL_MODEL_STATUS_ONLY");
|
MY_LOG_I("CONTROL_MODEL_STATUS_ONLY");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void iec61850s_setting_callback(stru_mms_s_setting *p_setting, const char *p_data)
|
LOCAL int iec61850s_control_signals_init(std::vector<stru_mms_s_signal_base> &vec_co)
|
||||||
|
{
|
||||||
|
g_vec_control.clear();
|
||||||
|
g_vec_control.reserve(vec_co.size());
|
||||||
|
|
||||||
|
for(std::vector<stru_mms_s_signal_base>::iterator it = vec_co.begin(); it != vec_co.end(); ++it)
|
||||||
|
{
|
||||||
|
stru_mms_s_control control = {};
|
||||||
|
control.base = *it;
|
||||||
|
|
||||||
|
std::string desc = "";
|
||||||
|
|
||||||
|
if(0 != dc_get_yk_signal_info(control.base.saddr, desc, control.base.type, control.base.ctrl_model, &control.p_data))
|
||||||
|
{
|
||||||
|
MY_LOG_E("dc_get_yk_signal_info failed, saddr: %s, desc: %s", control.base.saddr, desc.c_str());
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
g_vec_control.push_back(control);
|
||||||
|
}
|
||||||
|
|
||||||
|
if(0 != mms_s_control_register(g_vec_control.data(), g_vec_control.size(), iec61850s_control_callback))
|
||||||
|
{
|
||||||
|
MY_LOG_E("mms_s_control_register failed");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
LOCAL void iec61850s_setting_callback(stru_mms_s_setting *p_setting, const char *p_data)
|
||||||
{
|
{
|
||||||
if(NULL == p_setting || NULL == p_data)
|
if(NULL == p_setting || NULL == p_data)
|
||||||
{
|
{
|
||||||
|
|
@ -128,7 +219,36 @@ void iec61850s_setting_callback(stru_mms_s_setting *p_setting, const char *p_dat
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void iec61850s_param_callback(stru_mms_s_param *p_param, const char *p_data, int setting_zone)
|
LOCAL int iec61850s_setting_signals_init(std::vector<stru_mms_s_signal_base> &vec_ao)
|
||||||
|
{
|
||||||
|
g_vec_setting.clear();
|
||||||
|
g_vec_setting.reserve(vec_ao.size());
|
||||||
|
|
||||||
|
for(std::vector<stru_mms_s_signal_base>::iterator it = vec_ao.begin(); it != vec_ao.end(); ++it)
|
||||||
|
{
|
||||||
|
stru_mms_s_setting setting = {};
|
||||||
|
setting.base = *it;
|
||||||
|
|
||||||
|
std::string desc = "";
|
||||||
|
|
||||||
|
if(0 != dc_get_ao_signal_info(setting.base.saddr, desc, setting.base.type, nullptr, setting.base.ctrl_model, &setting.p_data, nullptr))
|
||||||
|
{
|
||||||
|
MY_LOG_E("dc_get_ao_signal_info failed, saddr: %s, desc: %s", setting.base.saddr, desc.c_str());
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
g_vec_setting.push_back(setting);
|
||||||
|
}
|
||||||
|
|
||||||
|
if(0 != mms_s_setting_register(g_vec_setting.data(), g_vec_setting.size(), iec61850s_setting_callback))
|
||||||
|
{
|
||||||
|
MY_LOG_E("mms_s_setting_register failed");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
LOCAL void iec61850s_param_callback(stru_mms_s_param *p_param, const char *p_data, int setting_zone)
|
||||||
{
|
{
|
||||||
if(NULL == p_param || NULL == p_data)
|
if(NULL == p_param || NULL == p_data)
|
||||||
{
|
{
|
||||||
|
|
@ -175,63 +295,118 @@ void iec61850s_param_callback(stru_mms_s_param *p_param, const char *p_data, int
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
LOCAL int iec61850s_param_signals_init(std::vector<stru_mms_s_signal_base> &vec_param)
|
||||||
|
{
|
||||||
|
g_vec_param.clear();
|
||||||
|
g_vec_param.reserve(vec_param.size());
|
||||||
|
|
||||||
|
for(std::vector<stru_mms_s_signal_base>::iterator it = vec_param.begin(); it != vec_param.end(); ++it)
|
||||||
|
{
|
||||||
|
stru_mms_s_param param = {};
|
||||||
|
param.base = *it;
|
||||||
|
|
||||||
|
std::string desc = "";
|
||||||
|
std::vector<void *> p_data_vec;
|
||||||
|
|
||||||
|
if(0 != dc_get_param_signal_info(param.base.saddr, desc, param.base.type, nullptr, param.base.ctrl_model, &p_data_vec, nullptr))
|
||||||
|
{
|
||||||
|
MY_LOG_E("dc_get_param_signal_info failed, saddr: %s, desc: %s", param.base.saddr, desc.c_str());
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
param.param_num = p_data_vec.size();
|
||||||
|
for(uint8_t i = 0; i < param.param_num; ++i)
|
||||||
|
{
|
||||||
|
param.p_data[i] = p_data_vec[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
g_vec_param.push_back(param);
|
||||||
|
}
|
||||||
|
|
||||||
|
if(0 != mms_s_param_register(g_vec_param.data(), g_vec_param.size(), iec61850s_param_callback))
|
||||||
|
{
|
||||||
|
MY_LOG_E("mms_s_param_register failed");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
int iec61850s_signals_init()
|
||||||
|
{
|
||||||
|
stru_mms_cfg *p_cfg = mms_cfg_ptr_get();
|
||||||
|
if(NULL == p_cfg)
|
||||||
|
{
|
||||||
|
MY_LOG_E("mms_cfg_ptr_get failed");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
show_mms_xml(*p_cfg);
|
||||||
|
|
||||||
|
if(0 != iec61850s_st_signals_init(p_cfg->vec_st))
|
||||||
|
{
|
||||||
|
MY_LOG_E("iec61850s_st_signals_init failed");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(0 != iec61850s_mx_signals_init(p_cfg->vec_mx))
|
||||||
|
{
|
||||||
|
MY_LOG_E("iec61850s_mx_signals_init failed");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(0 != iec61850s_control_signals_init(p_cfg->vec_co))
|
||||||
|
{
|
||||||
|
MY_LOG_E("iec61850s_control_signals_init failed");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(0 != iec61850s_setting_signals_init(p_cfg->vec_ao))
|
||||||
|
{
|
||||||
|
MY_LOG_E("iec61850s_setting_signals_init failed");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(0 != iec61850s_param_signals_init(p_cfg->vec_param))
|
||||||
|
{
|
||||||
|
MY_LOG_E("iec61850s_param_signals_init failed");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
int app_iec61850s_init1(void *arg)
|
int app_iec61850s_init1(void *arg)
|
||||||
{
|
{
|
||||||
|
if(0 != parse_mms_xml("/mnt/RTU/test/config/MMS/mms_s.xml"))
|
||||||
|
{
|
||||||
|
MY_LOG_E("parse_mms_xml failed");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
mms_s_dbg_switch(true);
|
mms_s_dbg_switch(true);
|
||||||
mms_s_file_path_set("/mnt/RTU/test/");
|
mms_s_file_path_set("/mnt/RTU/test/");
|
||||||
mms_s_control_register(vec_control.data(), vec_control.size(), iec61850s_control_callback);
|
mms_s_value_update_register(&g_mms_s_value_update_cb);
|
||||||
|
if(NULL == g_mms_s_value_update_cb)
|
||||||
|
{
|
||||||
|
MY_LOG_E("g_mms_s_value_update_cb is NULL");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int app_iec61850s_init2(void *arg)
|
int app_iec61850s_init2(void *arg)
|
||||||
{
|
{
|
||||||
for(std::vector<stru_mms_s_setting>::iterator it = vec_setting.begin(); it != vec_setting.end(); ++it)
|
if(0 != iec61850s_signals_init())
|
||||||
{
|
{
|
||||||
std::string desc = "";
|
MY_LOG_E("iec61850s_signals_init failed");
|
||||||
uint8_t data_type = 0;
|
return -1;
|
||||||
uint8_t ctrl_type = 0;
|
|
||||||
|
|
||||||
if(0 != dc_get_ao_signal_info(it->base.saddr, desc, data_type, nullptr, ctrl_type, (void **)&it->data, nullptr))
|
|
||||||
{
|
|
||||||
MY_LOG_E("dc_get_ao_signal_info failed");
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
strcpy(it->base.desc, desc.c_str());
|
|
||||||
it->base.type = data_type;
|
|
||||||
it->base.ctrl_model = ctrl_type;
|
|
||||||
}
|
|
||||||
|
|
||||||
for(std::vector<stru_mms_s_param>::iterator it = vec_param.begin(); it != vec_param.end(); ++it)
|
|
||||||
{
|
|
||||||
std::string desc = "";
|
|
||||||
uint8_t data_type = 0;
|
|
||||||
uint8_t ctrl_type = 0;
|
|
||||||
std::vector<void *> vec_p_data = {};
|
|
||||||
|
|
||||||
if(0 != dc_get_param_signal_info(it->base.saddr, desc, data_type, nullptr, ctrl_type, &vec_p_data, nullptr))
|
|
||||||
{
|
|
||||||
MY_LOG_E("dc_get_param_signal_info failed");
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
strcpy(it->base.desc, desc.c_str());
|
|
||||||
it->base.type = data_type;
|
|
||||||
it->base.ctrl_model = ctrl_type;
|
|
||||||
|
|
||||||
it->param_num = vec_p_data.size();
|
|
||||||
for(uint8_t j = 0; j < it->param_num; j++)
|
|
||||||
{
|
|
||||||
it->data[j] = (uint8_t *)vec_p_data[j];
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
mms_s_setting_register(vec_setting.data(), vec_setting.size(), iec61850s_setting_callback);
|
if(0 != mms_s_init("/mnt/RTU/test/config/MMS/PCS.icd", 102))
|
||||||
mms_s_param_register(vec_param.data(), vec_param.size(), iec61850s_param_callback);
|
|
||||||
|
|
||||||
if(0 != mms_s_init("/mnt/RTU/test/file/MMS/PCS.icd", 102))
|
|
||||||
{
|
{
|
||||||
MY_LOG_E("mms_s_init failed");
|
MY_LOG_E("mms_s_init failed");
|
||||||
return -1;
|
return -1;
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,129 @@
|
||||||
|
#include "parse_xml.h"
|
||||||
|
|
||||||
|
|
||||||
|
using namespace tinyxml2;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
LOCAL const char *ele_St = "St";
|
||||||
|
LOCAL const char *ele_Mx = "Mx";
|
||||||
|
LOCAL const char *ele_Co = "Co";
|
||||||
|
LOCAL const char *ele_Ao = "Ao";
|
||||||
|
LOCAL const char *ele_Param = "Param";
|
||||||
|
|
||||||
|
LOCAL const char *ele_Signal = "Signal";
|
||||||
|
|
||||||
|
LOCAL const char *attr_No = "no";
|
||||||
|
LOCAL const char *attr_Link = "link";
|
||||||
|
LOCAL const char *attr_Desc = "desc";
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
LOCAL stru_mms_cfg g_cfg = {};
|
||||||
|
|
||||||
|
std::map<std::string, std::vector<stru_mms_s_signal_base> *> g_vec_map_signal =
|
||||||
|
{
|
||||||
|
{ele_St, &g_cfg.vec_st},
|
||||||
|
{ele_Mx, &g_cfg.vec_mx},
|
||||||
|
{ele_Co, &g_cfg.vec_co},
|
||||||
|
{ele_Ao, &g_cfg.vec_ao},
|
||||||
|
{ele_Param, &g_cfg.vec_param},
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
LOCAL int parse_base(XMLElement *root)
|
||||||
|
{
|
||||||
|
if(root == nullptr)
|
||||||
|
{
|
||||||
|
MY_LOG_E("root is nullptr");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
for(std::map<std::string, std::vector<stru_mms_s_signal_base> *>::iterator it = g_vec_map_signal.begin(); it != g_vec_map_signal.end(); ++it)
|
||||||
|
{
|
||||||
|
XMLElement *ele = root->FirstChildElement(it->first.c_str());
|
||||||
|
if(ele == nullptr)
|
||||||
|
{
|
||||||
|
MY_LOG_E("FirstChildElement failed, ele: %s", it->first.c_str());
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
XMLElement *signal_ele = ele->FirstChildElement(ele_Signal);
|
||||||
|
while(signal_ele != nullptr)
|
||||||
|
{
|
||||||
|
stru_mms_s_signal_base base = {0};
|
||||||
|
std::string saddr = signal_ele->Attribute(attr_Link) ? signal_ele->Attribute(attr_Link) : "";
|
||||||
|
// std::string desc = signal_ele->Attribute(attr_Desc) ? signal_ele->Attribute(attr_Desc) : "";
|
||||||
|
|
||||||
|
if(saddr.empty() || saddr.length() > MMS_S_STR_LEN - 1)
|
||||||
|
{
|
||||||
|
MY_LOG_E("saddr is empty or length is too long, saddr: %s, len: %d", saddr.c_str(), saddr.length());
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
strcpy(base.saddr, saddr.c_str());
|
||||||
|
base.type = 0;
|
||||||
|
base.ctrl_model = 0;
|
||||||
|
it->second->push_back(base);
|
||||||
|
signal_ele = signal_ele->NextSiblingElement(ele_Signal);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
int parse_mms_xml(const std::string &path)
|
||||||
|
{
|
||||||
|
XMLDocument doc;
|
||||||
|
if(XML_SUCCESS != doc.LoadFile(path.c_str()))
|
||||||
|
{
|
||||||
|
MY_LOG_E("LoadFile failed, path: %s", path.c_str());
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
XMLElement *root = doc.RootElement();
|
||||||
|
if(root == nullptr)
|
||||||
|
{
|
||||||
|
MY_LOG_E("RootElement is nullptr");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(0 != parse_base(root))
|
||||||
|
{
|
||||||
|
MY_LOG_E("parse_base failed");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void show_mms_xml(stru_mms_cfg &cfg)
|
||||||
|
{
|
||||||
|
std::map<std::string, std::vector<stru_mms_s_signal_base> *> vec_map =
|
||||||
|
{
|
||||||
|
{ele_St, &cfg.vec_st},
|
||||||
|
{ele_Mx, &cfg.vec_mx},
|
||||||
|
{ele_Co, &cfg.vec_co},
|
||||||
|
{ele_Ao, &cfg.vec_ao},
|
||||||
|
{ele_Param, &cfg.vec_param},
|
||||||
|
};
|
||||||
|
|
||||||
|
for(auto &it : vec_map)
|
||||||
|
{
|
||||||
|
MY_LOG_I("ele: %s, size: %d", it.first.c_str(), it.second->size());
|
||||||
|
|
||||||
|
for(int i = 0; i < it.second->size(); ++i)
|
||||||
|
{
|
||||||
|
MY_LOG_I("saddr: %s, desc: %s, type: %d, ctrl_model: %d", it.second->at(i).saddr, it.second->at(i).desc, it.second->at(i).type, it.second->at(i).ctrl_model);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
stru_mms_cfg *mms_cfg_ptr_get(void)
|
||||||
|
{
|
||||||
|
return &g_cfg;
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,30 @@
|
||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<Root>
|
||||||
|
<St>
|
||||||
|
<Signal no="0" link="iec61850m.prj.st.0" desc="遥信01" />
|
||||||
|
<Signal no="1" link="iec61850m.prj.st.1" desc="遥信02" />
|
||||||
|
<Signal no="2" link="iec61850m.prj.st.2" desc="遥信03" />
|
||||||
|
<Signal no="3" link="iec61850m.prj.st.3" desc="遥信04" />
|
||||||
|
<Signal no="4" link="iec61850m.prj.st.4" desc="低频保护软压板" />
|
||||||
|
</St>
|
||||||
|
<Mx>
|
||||||
|
<Signal no="0" link="iec61850m.prj.mx.0" desc="遥测01" />
|
||||||
|
<Signal no="1" link="iec61850m.prj.mx.1" desc="遥测02" />
|
||||||
|
<Signal no="2" link="iec61850m.prj.mx.2" desc="遥测03" />
|
||||||
|
<Signal no="3" link="iec61850m.prj.mx.3" desc="遥测04" />
|
||||||
|
</Mx>
|
||||||
|
<Co>
|
||||||
|
<Signal no="0" link="iec61850m.prj.co.0" desc="遥控01"/>
|
||||||
|
<Signal no="1" link="iec61850m.prj.co.1" desc="遥控02"/>
|
||||||
|
<Signal no="2" link="iec61850m.prj.co.2" desc="遥控03"/>
|
||||||
|
<Signal no="3" link="iec61850m.prj.co.3" desc="遥控04"/>
|
||||||
|
<Signal no="4" link="iec61850m.prj.co.4" desc="低频保护软压板"/>
|
||||||
|
</Co>
|
||||||
|
<Ao>
|
||||||
|
<Signal no="0" link="iec61850m.prj.ao.0" desc="参数01" />
|
||||||
|
<Signal no="1" link="iec61850m.prj.ao.1" desc="参数02" />
|
||||||
|
</Ao>
|
||||||
|
<Param>
|
||||||
|
<Signal no="0" link="iec61850m.prj.param.0" desc="定值01" />
|
||||||
|
</Param>
|
||||||
|
</Root>
|
||||||
Loading…
Reference in New Issue