ems/ems_c/logic/logic_main.c

385 lines
12 KiB
C
Raw Normal View History

2025-05-13 17:49:49 +08:00
/*****************************************************************************
* @copyright 2024-202, . POWER SUPPLY CO., LTD.
* @file logic_main.c
* @brief xxxx
* @author Gary
* @date 2024/09/29
* @remark
*****************************************************************************/
#include "logic_main.h"
logic_pthread_t stlogic = {0};
tast_register_execute *task_group[E_TACTIC_MODE_END] = {0}; // MAX_TASK_NUM改用枚举
// 用于log打印 与 work_mode_e 强绑定
const char *workModeNames[] = {
"",
"调试模式",
"削峰填谷模式",
"需求响应模式",
"负载跟踪模式",
"需量控制",
"功率因数",
"null"};
/*********************************************************************
* @brief
* @param[in]
* @return 0sucessful1fault
*********************************************************************/
static int initTaskParam()
{
logic_getProtectParam();
logic_getPowerDistrParam();
work_mode_set_t tempMode;
if (0 == kit_get_work_mode_set(&tempMode))
{
stlogic.para_delivery.mode = tempMode.workMode;
}
else if ((uint8_t)getRtdbPointValue(rtdbType, kDev_Type_EMS, 0, kEms_LogicLog_Enable) == 1)
{
KITLOG(LOG_MODBUS_EN, INFO_EN, "获取调试配置失败 %s ==> %s", workModeNames[stlogic.para_delivery.mode], workModeNames[tempMode.workMode]);
KITPTF(LOG_MODBUS_EN, INFO_EN, "获取调试配置失败 %s ==> %s", workModeNames[stlogic.para_delivery.mode], workModeNames[tempMode.workMode]);
return 1;
}
else
{
return 1;
}
// 读取参数值
switch (stlogic.para_delivery.mode)
{
case E_TACTIC_MODE_DEBUG: // 调试模式
logic_debugParamUpdate();
break;
case E_TACTIC_MODE_PEAKVALLY: // 削峰填谷模式
logic_peakValleyUpdate();
break;
case E_TACTIC_MODE_DEMANDRES: // 需求响应模式
/* 暂未实现 */
break;
case E_TACTIC_MODE_LOADTRACK: // 负载跟踪模式
/* 暂未实现 */
break;
case E_TACTIC_MODE_DMDCTRL: // 需量控制模式
/* 暂未实现 */
break;
case E_TACTIC_MODE_PFCTRL: // 功率因数模式
/* 暂未实现 */
break;
default:
/*无模式*/
break;
}
return 0;
}
/*********************************************************************
* @brief
* @param[in] task_func
* @return NULL
*********************************************************************/
// 初始化任务链表节点
tast_register_execute *register_task(task_func_t task_func)
{
tast_register_execute *new_task = (tast_register_execute *)malloc(sizeof(tast_register_execute));
if (new_task == NULL)
{
printf("Memory allocation failed!\n");
return NULL;
}
// new_task->taskPeriod = period;
new_task->task = task_func;
new_task->next = NULL;
return new_task;
}
/*********************************************************************
* @brief
* @param[in] count
* @param[in] ...
* @return NULL
*********************************************************************/
tast_register_execute *init_task_list(int count, ...)
{
if (count <= 0)
return NULL; // 确保任务数量合法
va_list args; // 用于处理可变参数
va_start(args, count); // 初始化可变参数列表
tast_register_execute *head = NULL, *current = NULL;
// 循环遍历每个任务函数
for (int i = 0; i < count; i++)
{
task_func_t task_func = va_arg(args, task_func_t); // 获取当前任务函数指针
tast_register_execute *new_task = register_task(task_func);
if (new_task == NULL)
{
// 内存分配失败时,清理已分配的节点并返回 NULL
// free_task_list(head);
va_end(args); // 清理可变参数列表
return NULL;
}
if (head == NULL)
{
// 第一个任务作为头节点
head = new_task;
}
else
{
// 将新任务链接到链表末尾
current->next = new_task;
}
current = new_task; // 更新当前任务
}
va_end(args); // 结束可变参数处理
return head;
}
/*********************************************************************
* @brief
* @param[in]
* @return 0sucessful1fault
*********************************************************************/
static int logic_initTaskRegister()
{
INIT_TASK_GROUP();
for (int i = 0; i < E_TACTIC_MODE_END; i++)
{
if (task_group[i] == NULL)
{
printf("Failed to initialize task group 0.\n");
return 1; // 错误返回
}
}
return 0;
}
/*********************************************************************
* @brief 线
* @param[in]
* @return
*********************************************************************/
static int creatLogicTaskEntry()
{
if (pthread_create(&stlogic.tfd, NULL, creatLogicTaskThread, (void *)&stlogic.para_delivery) == 0)
{
KITPTF(LOG_LOGIC_EN, INFO_EN, "task线程创建成功");
KITLOG(LOG_LOGIC_EN, INFO_EN, "task线程创建成功");
return 0;
}
else
{
return 1;
}
}
/*********************************************************************
* @brief
* @param[in]
* @return 0sucessful1fault
*********************************************************************/
int creatLogicCtrTaskEntry()
{
initTaskParam();
if (logic_initTaskRegister() != 0)
{
return 1;
}
if (creatLogicTaskEntry() != 0)
{
return 1;
}
return 0;
}
/*********************************************************************
* @brief ,
* @param[in]
* @return
*********************************************************************/
void logic_taskTrigger()
{
int modeChange = 0;
// 读取是否参数更新
for (u_int16_t i = kSign_Logic_Start; i < kSign_Logic_End; i++)
{
stlogic.para_delivery.ParaChangeSign.ParaChangeUnion |= ((readWebSign(kSign_ShMem, i) == LOGIC_SIGN_MESSAGE) << i);
}
// 读取是否切换模式
if (LOGIC_SIGN_MESSAGE == readWebSign(kSign_ShMem, kSign_LogicMode))
{
writeWebSign(kSign_ShMem, kSign_LogicMode, 0);
modeChange = 1;
work_mode_set_t tempMode;
if (0 != kit_get_work_mode_set(&tempMode))
{
if ((uint8_t)getRtdbPointValue(rtdbType, kDev_Type_EMS, 0, kEms_LogicLog_Enable) == 1)
{
KITLOG(LOG_LOGIC_EN, INFO_EN, "获取调试配置失败 模式切换失败!!! %s ==> %s",workModeNames[stlogic.para_delivery.mode],workModeNames[tempMode.workMode]);
KITPTF(LOG_LOGIC_EN, INFO_EN, "获取调试配置失败 模式切换失败!!! %s ==> %s",workModeNames[stlogic.para_delivery.mode],workModeNames[tempMode.workMode]);
return;
}
}
if ((uint8_t)getRtdbPointValue(rtdbType, kDev_Type_EMS, 0, kEms_LogicLog_Enable) == 1)
{
KITLOG(LOG_LOGIC_EN, INFO_EN, "模式切换 %s ==> %s",workModeNames[stlogic.para_delivery.mode],workModeNames[tempMode.workMode]);
KITPTF(LOG_LOGIC_EN, INFO_EN, "模式切换 %s ==> %s",workModeNames[stlogic.para_delivery.mode],workModeNames[tempMode.workMode]);
return;
}
stlogic.para_delivery.mode = tempMode.workMode;
}
stlogic.para_delivery.task_params.protect.protectSign = (readWebSign(kSign_ShMem, kSign_Protect) == LOGIC_SIGN_MESSAGE);
stlogic.para_delivery.task_params.distr.powerSign = (readWebSign(kSign_ShMem, kSign_ActivePower) == LOGIC_SIGN_MESSAGE);
//数据库获取参数
/****保护****/
if (LOGIC_SIGN_MESSAGE == stlogic.para_delivery.task_params.protect.protectSign)
{
if (1 == logic_getProtectParam())
{
KITLOG(LOG_LOGIC_EN, INFO_EN, "保护参数错误");
KITPTF(LOG_LOGIC_EN, INFO_EN, "保护参数错误");
return;
}
stlogic.para_delivery.task_params.protect.protectSign = LOGIC_SIGN_UPLOAD;
}
/****功率分配****/
if (LOGIC_SIGN_MESSAGE == stlogic.para_delivery.task_params.distr.powerSign)
{
if (1 == logic_getPowerDistrParam())
{
KITLOG(LOG_LOGIC_EN, INFO_EN, "分配参数错误");
KITPTF(LOG_LOGIC_EN, INFO_EN, "分配参数错误");
return;
}
// 成功读完清除标志
stlogic.para_delivery.task_params.distr.powerSign = LOGIC_SIGN_UPLOAD;
}
//判定是否模式和参数统一
switch (stlogic.para_delivery.mode)
{
case E_TACTIC_MODE_DEBUG: // 调试模式
if (stlogic.para_delivery.ParaChangeSign.bits.debug || modeChange)
{
writeWebSign(kSign_ShMem, kSign_LogicDebug, LOGIC_SIGN_NONE);
if (1 == logic_debugParamUpdate())
{
KITLOG(LOG_LOGIC_EN, INFO_EN, "调试参数错误");
KITPTF(LOG_LOGIC_EN, INFO_EN, "调试参数错误");
}
// 成功读完清除标志
stlogic.para_delivery.ParaChangeSign.bits.debug = LOGIC_SIGN_NONE;
}
break;
case E_TACTIC_MODE_PEAKVALLY: // 削峰填谷模式
if (stlogic.para_delivery.ParaChangeSign.bits.peakValley || modeChange)
{
writeWebSign(kSign_ShMem, kSign_LogicPeakValley, LOGIC_SIGN_NONE);
if (1 == logic_peakValleyUpdate())
{
KITLOG(LOG_LOGIC_EN, INFO_EN, "削峰填谷参数错误");
KITPTF(LOG_LOGIC_EN, INFO_EN, "削峰填谷参数错误");
}
// 成功读完清除标志
stlogic.para_delivery.ParaChangeSign.bits.peakValley = LOGIC_SIGN_NONE;
}
break;
case E_TACTIC_MODE_DEMANDRES: // 需求响应模式
/* 暂未实现 */
break;
case E_TACTIC_MODE_LOADTRACK: // 负载跟踪模式
/* 暂未实现 */
break;
case E_TACTIC_MODE_DMDCTRL: // 需量控制
/* 暂未实现 */
break;
case E_TACTIC_MODE_PFCTRL: // 功率因数
/* 暂未实现 */
break;
default:
/*无模式*/
stlogic.para_delivery.task_params.distr.power = 0;
stlogic.para_delivery.task_params.protect.power = 0;
break;
}
}
/*********************************************************************
* @brief
* @param[in] task_param
* @return 0: , 1:
*********************************************************************/
int logic_taskExe(work_mode_e mode)
{
if (mode >= E_TACTIC_MODE_END)
{
// printf("Invalid task group index!\n");
return 1; // 返回错误
}
tast_register_execute *current = task_group[mode];
// 遍历并执行任务链表中的所有任务
while (current != NULL)
{
current->task(); // 执行当前任务
current = current->next; // 移动到下一个任务
}
return 0; // 成功
}
/*****************************************************************************
* @brief 线
* @param[in]
* @return
*****************************************************************************/
void *creatLogicTaskThread(void *arg)
{
task_params_t *task_param_in = (task_params_t *)arg;
while (stlogic.exitTaskFlag == 0)
{
logic_taskTrigger();
logic_getRTDBParams();
if (0 != logic_taskExe(task_param_in->mode))
{
// 处理调度错误,可以记录日志
KITLOG(LOG_LOGIC_EN, ERROR_EN, "任务调度失败,参数无效");
usleep(50000); // 50ms sleep
continue;
}
logic_paramUpload();
usleep(20000); // 20ms sleep
}
pthread_exit(NULL);
}
void example_task1()
{
;
}