@ -30,11 +30,11 @@ static void set_light2breathtimeout(void);
static void set_light2net_cfg_done ( void ) ;
static void start_breath_timer ( void ) ;
static void report_switch_status ( void ) ;
void calculate_pwm_duty ( void ) ;
void calculate_pwm_duty ( device_control_t * pdevice_control ) ;
void close_light ( void ) ;
// 定义上报函数类型
typedef void ( * report_func_t ) ( void ) ;
static void start_report_task ( report_func _t report_func ) ;
static void start_report_task ( uint32 _t report_mask ) ;
static void report_fade_complete_status ( void ) ;
static uint8_t calculate_checksum ( const device_data_t * data ) ;
static bool write_device_data_to_addr ( uint32_t addr , const device_data_t * data ) ; ;
@ -56,6 +56,10 @@ static void report_device_online_status(void);
static osal_task * report_task_handle = NULL ;
static bool report_task_running = false ; // 添加任务运行状态标志
// 新增:全局上报掩码变量和条件变量
static uint32_t g_report_mask = 0 ;
static osal_semaphore report_sem ; // 条件变量, 用于唤醒report task
// 灯渐变任务相关定义
# define FADE_TASK_PRIO 80
# define FADE_TASK_STACK_SIZE 0x1000
@ -64,9 +68,6 @@ static bool report_task_running = false; // 添加任务运行状态标志
# define BREATH_TASK_PRIO 80
# define BREATH_TASK_STACK_SIZE 0x1000
// PWM频率和周期定义
# define PWM_FREQUENCY 2000 // PWM频率 2KHz
static uint32_t pwm_period_cnt = 0 ; // PWM周期 40us
static uint8_t channel_id_cw = 0 ; // 冷白LED通道ID
static uint8_t channel_id_ww = 0 ; // 暖白LED通道ID
@ -101,28 +102,31 @@ typedef struct {
const char * prefix ; // 打印前缀
} print_limiter_t ;
# define FADE_CTRL_DATA_SIZE(fade_ctx) ((fade_ctx).member_barrier - (uint8_t*)&(fade_ctx))
// 渐变控制相关变量
static struct fade_ctx_t {
// 渐变控制参数
int32_t target_brightness ;
int32_t target_cct ;
int32_t current_brightness ;
int32_t current_cct ;
int32_t step_brightness ;
int32_t step_cct ;
bool is_fading ;
bool fade_completed ;
uint32_t smooth_time_us ; // 渐变总时长(us)
uint32 _t update_interval ; // 更新间隔(us)
struct {
// 渐变控制参数
int32_t target_brightness ;
int32_t target_cct ;
int32_t current_brightness ;
int32_t current_cct ;
int32_t step_brightness ;
int32_t step_cct ;
bool is_fading ;
bool fade_completed ;
uint16 _t fade_time ; //s
uint32_t smooth_time_us ; // 渐变总时长(us)
uint32_t update_interval ; // 更新间隔(us)
// 打印限制器
print_limiter_t print_limiter ;
} ;
uint8_t member_barrier [ 0 ] ; // 用于计算前面成员变量大小
// 任务相关
osal_task * task_handle ;
bool task_running ;
osal_semaphore sem ;
timer_handle_t timer_handle ;
// 打印限制器
print_limiter_t print_limiter ;
} fade_ctx = { 0 } ;
// 呼吸灯控制相关变量
@ -191,7 +195,7 @@ static void *fade_task(const char *arg)
{
unused ( arg ) ;
e_printf ( " [fade_task] Task started \r \n " ) ;
device_control_t device_control = { } ;
while ( fade_ctx . task_running ) {
// 等待渐变信号
if ( osal_sem_down_timeout ( & fade_ctx . sem , 100 * 1000 ) ! = OSAL_SUCCESS ) {
@ -242,18 +246,22 @@ static void *fade_task(const char *arg)
BRIGHTNESS_LITME_RANGE ( fade_ctx . current_brightness ) ;
CCT_LITME_RANGE ( fade_ctx . current_cct ) ;
// 更新PWM输出
g_ device_control. brightness_local = fade_ctx . current_brightness ;
g_ device_control. cct_local = fade_ctx . current_cct ;
calculate_pwm_duty ( ) ;
update_pwm_output ( g_device_control . on , g_ device_control. duty_cw , g_ device_control. duty_ww ) ;
device_control . brightness_local = fade_ctx . current_brightness ;
device_control . cct_local = fade_ctx . current_cct ;
calculate_pwm_duty ( & device_control ) ;
update_pwm_output ( g_device_control . on , device_control . duty_cw , device_control . duty_ww ) ;
if ( fade_ctx . fade_completed ) {
fade_ctx . fade_completed = false ;
g_device_control . duty_ww = device_control . duty_ww ;
g_device_control . duty_cw = device_control . duty_cw ;
g_device_control . brightness_local = fade_ctx . current_brightness ;
g_device_control . cct_local = fade_ctx . current_cct ;
e_printf ( " [fade_task] Status report: local brightness=%d, CCT=%d \r \n " ,
g_device_control . brightness_local ,
g_device_control . cct_local ) ;
// 启动状态上报任务,使用渐变完成状态上报函数
start_report_task ( report_device_online_status ) ;
start_report_task ( REPORT_BRIGHTNESS | REPORT_CCT ) ;
req_save_device_data ( ) ;
}
}
@ -316,7 +324,7 @@ static void *breath_task(const char *arg)
// 渐变定时器回调函数
static void fade_timer_callback ( uintptr_t data )
{
osal_sem_up ( & fade_ctx . sem ) ;
osal_sem_up ( & fade_ctx . sem ) ; // 唤醒渐变任务 fade_task
uapi_timer_start ( fade_ctx . timer_handle , fade_ctx . update_interval , fade_timer_callback , 0 ) ;
}
@ -361,6 +369,8 @@ static void init_fade_ctx(void)
// 设置默认更新间隔
fade_ctx . update_interval = FADE_INTERVAL_MIN ;
fade_ctx . current_brightness = g_device_control . brightness_local ;
fade_ctx . current_cct = g_device_control . cct_local ;
}
// 初始化呼吸灯控制
@ -455,16 +465,16 @@ static void stop_breath_timer(void)
}
// 计算PWM占空比
void calculate_pwm_duty ( void )
void calculate_pwm_duty ( device_control_t * pdevice_control )
{ // 如果开关关闭, 则占空比为0
uint32_t total_brightness_pwm = g_ device_control. brightness_local ;
uint32_t total_brightness_pwm = p device_control- > brightness_local ;
// 计算色温比例 (0-10000)
uint16_t cct_ratio = ( ( g_ device_control. cct_local - CCT_LOCAL_MIN ) * 10000 ) / CCT_RANGE ;
uint16_t cct_ratio = ( ( p device_control- > cct_local - CCT_LOCAL_MIN ) * 10000 ) / CCT_RANGE ;
// 根据色温比例计算CW和WW的占空比
// 总亮度保持不变, 只调整CW和WW的比例
g_ device_control. duty_cw = ( total_brightness_pwm * cct_ratio ) / 10000 ;
g_ device_control. duty_ww = total_brightness_pwm - g_ device_control. duty_cw ;
p device_control- > duty_cw = ( total_brightness_pwm * cct_ratio ) / 10000 ;
p device_control- > duty_ww = total_brightness_pwm - p device_control- > duty_cw ;
}
// 更新PWM输出
@ -496,15 +506,18 @@ void update_pwm_output(bool on_state, uint16_t duty_cw_val, uint16_t duty_ww_val
low_cnt_ww = pwm_period_cnt ; // Ensure low_cnt is full period if off
}
// uapi_pwm_stop_group(CONFIG_PWM_GROUP_ID);
cfg_repeat . high_time = high_cnt_cw ;
cfg_repeat . low_time = low_cnt_cw ;
uapi_pwm_open ( channel_id_cw , & cfg_repeat ) ;
// uapi_pwm_update_duty_ratio(channel_id_cw, cfg_repeat.low_time, cfg_repeat.high_time);
cfg_repeat . high_time = high_cnt_ww ;
cfg_repeat . low_time = low_cnt_ww ;
cfg_repeat . offset_time = high_cnt_cw ; // WW PWM starts after CW PWM high time
uapi_pwm_open ( channel_id_ww , & cfg_repeat ) ;
// uapi_pwm_update_duty_ratio(channel_id_ww, cfg_repeat.low_time, cfg_repeat.high_time);
uapi_pwm_start_group ( CONFIG_PWM_GROUP_ID ) ;
@ -517,74 +530,78 @@ void update_pwm_output(bool on_state, uint16_t duty_cw_val, uint16_t duty_ww_val
# define ABS(x) ((x) < 0 ? -(x) : (x))
// 计算渐变步长
static void calculate_fade_steps ( void )
static void calculate_fade_steps ( struct fade_ctx_t * pfade_ctx )
{
// 从g_device_control获取渐变时间
fade_ctx . smooth_time_us = g_device_control . fade_time * 1000 * 1000 ; //s->us
e_printf ( " fade brightness: curr:%d, target:%d, cct: curr:%d, target :%d \r \n " ,
fade_ctx . current_brightness , fade_ctx . target_brightness , fade_ctx . current_cct , fade_ctx . target_cct ) ;
p fade_ctx- > smooth_time_us = pfade_ctx - > fade_time * 1000 * 1000 ; //s->us
e_printf ( " fade brightness:%d->%d, cct:%d->%d, time :%ds \r \n " ,
p fade_ctx- > current_brightness , p fade_ctx- > target_brightness , p fade_ctx- > current_cct , p fade_ctx- > target_cct , pfade_ctx - > fade_time );
// 计算亮度渐变步长
int32_t brightness_diff = fade_ctx . target_brightness - fade_ctx . current_brightness ;
int32_t cct_diff = fade_ctx . target_cct - fade_ctx . current_cct ;
int32_t brightness_diff = p fade_ctx- > target_brightness - p fade_ctx- > current_brightness ;
int32_t cct_diff = p fade_ctx- > target_cct - p fade_ctx- > current_cct ;
// 计算需要的总步数(取亮度和色温中变化较大的那个)
uint32_t max_diff = ( ABS ( brightness_diff ) > ABS ( cct_diff ) ) ? ABS ( brightness_diff ) : ABS ( cct_diff ) ;
uint32_t min_steps = 0 ;
uint32_t available_interval = 0 ;
// 如果变化太小,直接设置目标值 EKKO:这里需要确认是直接设置目标值还是强制等待渐变时长
if ( max_diff = = 0 ) {
fade_ctx . step _brightness = 0 ;
fade_ctx . step_cct = 0 ;
fade_ctx . update_interval = fade_ctx . smooth_time_us ;
// 如果变化太小或者不需要渐变 ,直接设置目标值
if ( max_diff = = 0 | | pfade_ctx - > smooth_time_us = = 0 ) {
p fade_ctx- > current _brightness = pfade_ctx - > target_brightness ;
p fade_ctx- > current_cct = pfade_ctx - > target_cct ;
p fade_ctx- > step_brightness = 0 ;
pfade_ctx - > step_cct = 0 ;
pfade_ctx - > update_interval = FADE_INTERVAL_MIN ;
goto lab_exit ;
}
min_steps = max_diff ;
// 计算实际可用的时间间隔
available_interval = fade_ctx . smooth_time_us / min_steps ;
available_interval = p fade_ctx- > smooth_time_us / min_steps ;
// 如果时间间隔太小(小于允许的最小更新间隔),则增加步长
if ( available_interval < FADE_INTERVAL_MIN ) {
// 重新计算步长,确保在指定时间内完成
fade_ctx . update_interval = FADE_INTERVAL_MIN ;
int32_t actual_steps = fade_ctx . smooth_time_us / fade_ctx . update_interval ;
p fade_ctx- > update_interval = FADE_INTERVAL_MIN ;
int32_t actual_steps = p fade_ctx- > smooth_time_us / p fade_ctx- > update_interval ;
// 计算新的步长
fade_ctx . step_brightness = brightness_diff / actual_steps ;
fade_ctx . step_cct = cct_diff / actual_steps ;
p fade_ctx- > step_brightness = brightness_diff / actual_steps ;
p fade_ctx- > step_cct = cct_diff / actual_steps ;
// 确保至少有一个最小步长
if ( fade_ctx . step_brightness = = 0 & & brightness_diff ! = 0 ) {
fade_ctx . step_brightness = ( brightness_diff > 0 ) ? 1 : - 1 ;
if ( p fade_ctx- > step_brightness = = 0 & & brightness_diff ! = 0 ) {
p fade_ctx- > step_brightness = ( brightness_diff > 0 ) ? 1 : - 1 ;
}
if ( fade_ctx . step_cct = = 0 & & cct_diff ! = 0 ) {
fade_ctx . step_cct = ( cct_diff > 0 ) ? 1 : - 1 ;
if ( p fade_ctx- > step_cct = = 0 & & cct_diff ! = 0 ) {
p fade_ctx- > step_cct = ( cct_diff > 0 ) ? 1 : - 1 ;
}
} else {
// 使用计算出的时间间隔
fade_ctx . update_interval = available_interval ;
fade_ctx . step_brightness = ( brightness_diff > 0 ) ? 1 : - 1 ;
fade_ctx . step_cct = ( cct_diff > 0 ) ? 1 : - 1 ;
p fade_ctx- > update_interval = available_interval ;
p fade_ctx- > step_brightness = ( brightness_diff > 0 ) ? 1 : - 1 ;
p fade_ctx- > step_cct = ( cct_diff > 0 ) ? 1 : - 1 ;
}
// 如果亮度或色温没有变化, 则步长为0
if ( brightness_diff = = 0 ) {
fade_ctx . step_brightness = 0 ;
p fade_ctx- > step_brightness = 0 ;
}
if ( cct_diff = = 0 ) {
fade_ctx . step_cct = 0 ;
p fade_ctx- > step_cct = 0 ;
}
lab_exit :
if ( should _print( & fade_ctx . print_limiter ) ) {
e_printf ( " max_diff:%d, fade time:%uus, B rightness: diff:%d, step:%d, CCT: diff:%d, step:%d, update_interval:%uus \r \n " ,
max_diff , fade_ctx . smooth_time_us , brightness_diff , fade_ctx . step_brightness , cct_diff , fade_ctx . step_cct , fade_ctx . update_interval ) ;
}
e _printf ( " fade max_diff:%d, fade time:%uus, Brightness: diff:%d, step:%d, CCT: diff:%d, step:%d, update_interval:%uus \r \n " ,
max_diff , pfade_ctx - > smooth_time_us , b rightness_ diff, pfade_ctx - > step_brightness , cct_diff , pfade_ctx - > step_cct , pfade_ctx - > update_interval ) ;
}
static void cancel_current_light_fade ( void )
{
uapi_timer_stop ( fade_ctx . timer_handle ) ;
// 如果我打断了渐变,则将当前值更新到目标值不然下次计算会异常
// g_device_control.cct_local = fade_ctx.current_cct;
// g_device_control.brightness_local = fade_ctx.current_brightness;
// memset(&fade_ctx, 0, FADE_CTRL_DATA_SIZE(fade_ctx));
}
// 计算校验和
@ -834,88 +851,113 @@ static void stop_save_task(void)
}
// 设置灯光状态(统一控制函数)
int set_light ( int32_t brightness_local , int32_t cct_local )
// 参数:
// source: 控制源,用于区分不同的控制场景
// current_brightness_local: 当前亮度值
// current_cct_local: 当前色温值
// brightness_local_target: 亮度目标值
// cct_local_target: 色温目标值
// 返回值:
// 0: 成功
// -111: 异步上报
// -1: 失败
int set_light ( light_ctrl_source_e source ,
int32_t brightness_local_target , int32_t cct_local_target )
{
struct fade_ctx_t tmp_fade_ctx = fade_ctx ;
// 如果任一参数大于等于0, 则更新对应值
e_printf ( " ligMode:%d, local brightness: curr:%d, target:%d, local cct: curr:%d, target:%d \r \n " ,
g_device_control . elightMode , g_device_control . brightness_local , brightness_local , g_device_control . cct_local , cct_local ) ;
tmp_fade_ctx . current_brightness = g_device_control . brightness_local ;
tmp_fade_ctx . current_cct = g_device_control . cct_local ;
tmp_fade_ctx . target_brightness = tmp_fade_ctx . current_brightness ;
tmp_fade_ctx . target_cct = tmp_fade_ctx . current_cct ;
if ( brightness_local > = 0 ) {
BRIGHTNESS_LITME_RANGE ( brightness_local ) ;
if ( g_device_control . elightMode = = LIGHT_MODE_CUSTOMER ) {
tmp_fade_ctx . target_brightness = brightness_local ;
} else {
g_device_control . brightness_local = brightness_local ;
}
}
if ( cct_local > = 0 ) {
CCT_LITME_RANGE ( cct_local ) ;
if ( g_device_control . elightMode = = LIGHT_MODE_CUSTOMER ) {
tmp_fade_ctx . target_cct = cct_local ;
} else {
g_device_control . cct_local = cct_local ;
}
}
switch ( g_device_control . elightMode )
{
case LIGHT_MODE_CUSTOMER :
if ( g_device_control . fade_time ) {
tmp_fade_ctx . is_fading = true ;
tmp_fade_ctx . fade_completed = false ;
// if(fade_ctx.is_fading) {
// e_printf("fade is running, skip set_light\r\n");
// return -111;
// }
fade_ctx = tmp_fade_ctx ;
// 计算渐变步长
calculate_fade_steps ( ) ;
e_printf ( " start fade \r \n " ) ;
// 启动渐变定时器
set_switch ( true ) ;
uapi_timer_start ( fade_ctx . timer_handle , fade_ctx . update_interval , fade_timer_callback , 0 ) ;
fast_report ( SVC_ID_LIGHT_MODE ) ;
#if 0
等待渐变完成
while (!fade_ctx.fade_completed) {
msleep(10);
}
return 0; // 同步上报
#else
return - 111 ; // 异步上报
# endif
}
g_device_control . cct_local = tmp_fade_ctx . target_cct ;
g_device_control . brightness_local = tmp_fade_ctx . target_brightness ;
// no break; // 如果渐变时间是0则直接一步完成
default : //情景模式直接切换到对应的色温和亮度
set_switch ( true ) ;
}
start_report_task ( report_device_online_status ) ; //直接全量上报
return - 111 ; // 异步上报
}
// 设置开关状态
int set_switch ( bool open )
{
g_device_control . on = open ;
if ( fade_ctx . is_fading ) //打断当前的渐变计划
{
struct fade_ctx_t tmp_fade_ctx = { 0 } ;
if ( fade_ctx . is_fading ) {
cancel_current_light_fade ( ) ;
}
calculate_pwm_duty ( ) ;
update_pwm_output ( g_device_control . on , g_device_control . duty_cw , g_device_control . duty_ww ) ;
uapi_gpio_set_val ( SWITCH_PIN , open ? OPEN_LIGHT : CLOSE_LIGHT ) ;
// 如果打开灯,则需要手动将前置状态设置为关闭的样子,这样子后面计算渐变才能正常计算
if ( APP_OPEN_LIGHT = = source ) {
g_device_control . on = true ;
fade_ctx . current_brightness = 0 ;
fade_ctx . current_cct = g_device_control . cct_local ;
brightness_local_target = g_device_control . brightness_local ;
cct_local_target = g_device_control . cct_local ;
}
memcpy ( & tmp_fade_ctx , & fade_ctx , FADE_CTRL_DATA_SIZE ( fade_ctx ) ) ;
tmp_fade_ctx . target_brightness = tmp_fade_ctx . current_brightness ;
if ( brightness_local_target > = 0 ) {
BRIGHTNESS_LITME_RANGE ( brightness_local_target ) ;
tmp_fade_ctx . target_brightness = brightness_local_target ;
}
tmp_fade_ctx . target_cct = tmp_fade_ctx . current_cct ;
if ( cct_local_target > = 0 ) {
CCT_LITME_RANGE ( cct_local_target ) ;
tmp_fade_ctx . target_cct = cct_local_target ;
}
e_printf ( " source:%d, lightMode:%d, local brightness: base:%d, target:%d, local cct: base:%d, target:%d \r \n " ,
source , g_device_control . elightMode , tmp_fade_ctx . current_brightness ,
tmp_fade_ctx . target_brightness , tmp_fade_ctx . current_cct , tmp_fade_ctx . target_cct ) ;
tmp_fade_ctx . fade_time = g_device_control . fade_time ;
switch ( source ) {
case APP_CLOSE_LIGHT :
close_light ( ) ;
return 0 ;
break ;
case DEV_POWER_ON :
case APP_OPEN_LIGHT :
tmp_fade_ctx . fade_time = NORMAL_FADE_TIME ; // 上电时,直接设置为默认渐变时长
case APP_CHANGE_LIGHT_MODE :
// 直接将信息更新到目标值
g_device_control . cct_local = tmp_fade_ctx . target_cct ;
g_device_control . brightness_local = tmp_fade_ctx . target_brightness ;
//情景模式或者上电时直接切换到对应的色温和亮度
tmp_fade_ctx . is_fading = true ;
tmp_fade_ctx . fade_completed = false ;
if ( tmp_fade_ctx . is_fading ) {
cancel_current_light_fade ( ) ;
}
calculate_fade_steps ( & tmp_fade_ctx ) ;
memcpy ( & fade_ctx , & tmp_fade_ctx , FADE_CTRL_DATA_SIZE ( tmp_fade_ctx ) ) ;
e_printf ( " start fade \r \n " ) ;
uapi_timer_start ( fade_ctx . timer_handle , fade_ctx . update_interval , fade_timer_callback , 0 ) ;
start_report_task ( REPORT_SWITCH | REPORT_BRIGHTNESS | REPORT_CCT ) ;
req_save_device_data ( ) ;
return 0 ; // 异步上报
break ;
case APP_CHANGE_LIGHT_BRIGHTNESS_CCT :
// 直接将信息更新到目标值
g_device_control . cct_local = tmp_fade_ctx . target_cct ;
g_device_control . brightness_local = tmp_fade_ctx . target_brightness ;
tmp_fade_ctx . is_fading = true ;
tmp_fade_ctx . fade_completed = false ;
if ( tmp_fade_ctx . is_fading ) {
cancel_current_light_fade ( ) ;
}
calculate_fade_steps ( & tmp_fade_ctx ) ;
memcpy ( & fade_ctx , & tmp_fade_ctx , FADE_CTRL_DATA_SIZE ( tmp_fade_ctx ) ) ;
e_printf ( " start fade \r \n " ) ;
uapi_timer_start ( fade_ctx . timer_handle , fade_ctx . update_interval , fade_timer_callback , 0 ) ;
start_report_task ( REPORT_BRIGHTNESS | REPORT_CCT | REPORT_LIGHT_MODE ) ;
req_save_device_data ( ) ;
#if 0
等待渐变完成
while (!fade_ctx.fade_completed) {
msleep(10);
}
return 0; // 同步上报
#else
return - 111 ; // 异步上报
# endif
break ;
}
e_printf ( " set_light error, source:%d, current_brightness_local:%d, current_cct_local:%d, brightness_local_target:%d, cct_local_target:%d \r \n " ,
source , tmp_fade_ctx . current_brightness , tmp_fade_ctx . current_cct , brightness_local_target , cct_local_target ) ;
return - 1 ;
}
void close_light ( void )
{
g_device_control . on = false ;
if ( fade_ctx . is_fading ) {
cancel_current_light_fade ( ) ;
}
fade_ctx . current_brightness = 0 ;
fade_ctx . current_cct = 0 ;
update_pwm_output ( false , 0 , 0 ) ;
req_save_device_data ( ) ;
return 0 ;
}
static void gpio_init ( pin_t pin )
@ -950,10 +992,10 @@ static void pwm_init(pin_t pin, pin_t pin1)
channel_id_cw = pin % 8 ;
channel_id_ww = pin1 % 8 ;
uint8_t channel_ids [ 2 ] = { channel_id_cw , channel_id_ww } ;
uapi_pwm_open( channel_id_cw, & cfg_repeat) ;
uapi_pwm_open( channel_id_ww, & cfg_repeat) ;
// uapi_pwm_open( channel_id_cw, & cfg_repeat);
// uapi_pwm_open( channel_id_ww, & cfg_repeat);
uapi_pwm_set_group ( CONFIG_PWM_GROUP_ID , channel_ids , sizeof ( channel_ids ) ) ;
uapi_pwm_start_group( CONFIG_PWM_GROUP_ID) ;
// uapi_pwm_start_group( CONFIG_PWM_GROUP_ID);
e_printf ( " PWM基础时钟频率: %dHz, 目标时钟频率: %dHz, 周期计数: %d \r \n " , frequency , PWM_FREQUENCY , pwm_period_cnt ) ;
}
@ -981,11 +1023,12 @@ void stop_net_config(void) {
}
// 配网状态管理相关函数
static void handle_network_status ( void )
static int handle_network_status ( void )
{
uint8_t start_net_cfg = 0 ;
// 如果已经配网,直接返回
if ( g_device_control . is_networked ) {
return ;
return start_net_cfg ;
}
// 增加上电计数
@ -994,10 +1037,12 @@ static void handle_network_status(void)
// 检查是否需要进入配网状态
if ( ( ! g_device_control . is_net_configured ) | | g_device_control . power_on_cnt > = NET_CFG_ENTRY_CNT ) {
start_net_config ( ) ;
start_net_cfg = 1 ;
}
// 保存设备状态
req_save_device_data ( ) ;
return start_net_cfg ;
}
@ -1031,46 +1076,93 @@ static void report_switch_status(void)
fast_report ( SVC_ID_SWITCH ) ;
}
static const struct {
const char * svc_id ;
} report_mask_map [ ] = {
[ REPORT_SWITCH ] = { SVC_ID_SWITCH } ,
[ REPORT_BRIGHTNESS ] = { SVC_ID_BRIGHTNESS } ,
[ REPORT_CCT ] = { SVC_ID_CCT } ,
[ REPORT_LIGHT_MODE ] = { SVC_ID_LIGHT_MODE } ,
[ REPORT_FADE_TIME ] = { SVC_ID_FADE_TIME } ,
} ;
// 状态上报任务函数
static void * report_task ( const char * arg )
{
report_func_t report_func = ( report_func_t ) arg ;
e_printf ( " report_task running... \r \n " ) ;
unused ( arg ) ;
e_printf ( " [ report_task] Task started \r \n " ) ;
// 等待hilink和数据ready
while ( ! ( g_device_control . read_done & & hf_hilink_main_is_runing ( ) ) ) {
// 数据已经正确load并且hilink已经运行才开始上报
e_printf ( " read_done%d, hilink:%d \r \n " , g_device_control . read_done , hf_hilink_main_is_runing ( ) ) ;
osal_msleep ( 50 ) ;
}
if ( report_func )
{
report_func ( ) ;
while ( report_task_running ) {
// 等待信号量唤醒
if ( g_report_mask = = 0 & & osal_sem_down_timeout ( & report_sem , 100 * 1000 ) ! = OSAL_SUCCESS ) {
continue ;
}
e_printf ( " [report_task] Reported mask: 0x%x \r \n " , g_report_mask ) ;
// 根据掩码进行上报
if ( g_report_mask & REPORT_SWITCH ) {
g_report_mask & = ~ REPORT_SWITCH ;
fast_report ( SVC_ID_SWITCH ) ;
}
if ( g_report_mask & REPORT_BRIGHTNESS ) {
g_report_mask & = ~ REPORT_BRIGHTNESS ;
fast_report ( SVC_ID_BRIGHTNESS ) ;
}
if ( g_report_mask & REPORT_CCT ) {
g_report_mask & = ~ REPORT_CCT ;
fast_report ( SVC_ID_CCT ) ;
}
if ( g_report_mask & REPORT_LIGHT_MODE ) {
g_report_mask & = ~ REPORT_LIGHT_MODE ;
fast_report ( SVC_ID_LIGHT_MODE ) ;
}
if ( g_report_mask & REPORT_FADE_TIME ) {
g_report_mask & = ~ REPORT_FADE_TIME ;
fast_report ( SVC_ID_FADE_TIME ) ;
}
}
report_task_running = false ;
e_printf ( " [report_task] exited \r \n " ) ;
e_printf ( " [report_task] Task exited \r \n " ) ;
return NULL ;
}
// 启动状态上报任务
static void start_report_task ( report_func _t report_func )
static void start_report_task ( uint32 _t report_mask )
{
if ( report_task_running ) {
e_printf ( " [ report_t ask] Previous task is still running, skip this report \r \n " ) ;
return ;
// 设置全局掩码
g_ report_m ask | = report_mask ;
osal_sem_up ( & report_sem ) ;
// 只在第一次创建任务
if ( ! report_task_running ) {
osal_kthread_lock ( ) ;
if ( report_task_running ) {
osal_kthread_unlock ( ) ;
return ;
}
report_task_running = true ;
e_printf ( " [start_report_task] Creating report task \r \n " ) ;
report_task_handle = osal_kthread_create ( ( osal_kthread_handler ) report_task , NULL , " ReportStaTask " ,
REPORT_TASK_STACK_SIZE ) ;
if ( report_task_handle ! = NULL ) {
osal_kthread_set_priority ( report_task_handle , REPORT_TASK_PRIO ) ;
e_printf ( " [start_report_task] Report task created successfully \r \n " ) ;
} else {
e_printf ( " [start_report_task] Failed to create report task \r \n " ) ;
report_task_running = false ;
}
osal_kthread_unlock ( ) ;
} else {
e_printf ( " [start_report_task] Report task already running, mask: 0x%x \r \n " , report_mask ) ;
}
report_task_running = true ; // 设置任务运行标志
if ( report_task_handle ) {
osal_kthread_destroy ( report_task_handle , 0 ) ;
report_task_handle = NULL ;
}
e_printf ( " start report_task \r \n " ) ;
osal_kthread_lock ( ) ;
report_task_handle = osal_kthread_create ( ( osal_kthread_handler ) report_task , ( void * ) report_func , " ReportStaTask " ,
REPORT_TASK_STACK_SIZE ) ;
if ( report_task_handle ! = NULL ) {
osal_kthread_set_priority ( report_task_handle , REPORT_TASK_PRIO ) ;
}
osal_kthread_unlock ( ) ;
}
static int device_online = 0 ;
@ -1094,8 +1186,8 @@ void handle_device_online(void)
// 重置配网状态
g_net_breath_state = NET_CFG_IDLE ;
g_net_cfg_start_time = 0 ;
// 启动状态上报任务,使用设备上线状态上报函数
start_report_task ( report_device_online_status ) ;
// 启动状态上报任务,上报所有服务状态
start_report_task ( REPORT_ALL ) ;
device_online = 1 ;
}
@ -1200,6 +1292,22 @@ static void stop_spotlight_main_task(void)
spotlight_main_task_handle = NULL ;
osal_kthread_unlock ( ) ;
// 停止report task
if ( report_task_running ) {
report_task_running = false ;
osal_sem_up ( & report_sem ) ; // 唤醒任务以使其退出
osal_kthread_lock ( ) ;
if ( report_task_handle ) {
osal_kthread_destroy ( report_task_handle , 0 ) ;
report_task_handle = NULL ;
}
osal_kthread_unlock ( ) ;
osal_sem_destroy ( & report_sem ) ;
e_printf ( " [stop_spotlight_main_task] Report task stopped \r \n " ) ;
}
e_printf ( " [stop_spotlight_main_task] Task stopped \r \n " ) ;
}
@ -1220,9 +1328,8 @@ static void check_net_cfg_timeout(void)
// 修改spotlight_main函数
int spotlight_main ( void ) {
uapi_systick_init ( ) ;
e_printf ( " uapi_timer_get_max_us:%uus, start_time:%uus \r \n " , uapi_timer_get_max_us ( ) , uapi_systick_get_ms ( ) ) ;
read_device_data ( ) ;
e_printf ( " uapi_timer_get_max_us:%uus \r \n " , uapi_timer_get_max_us ( ) ) ;
// 初始化GPIO并将灯关闭
gpio_init ( SWITCH_PIN ) ;
// 初始化PWM系统
@ -1235,10 +1342,19 @@ int spotlight_main(void) {
// 初始化保存任务
init_save_task ( ) ;
// 初始化report task信号量
if ( osal_sem_init ( & report_sem , 0 ) ! = OSAL_SUCCESS ) {
e_printf ( " [spotlight_main] Failed to init report semaphore \r \n " ) ;
return - 1 ;
}
// 检查配网状态,确定是否需要进入配网状态
handle_network_status ( ) ;
//上电亮灯也是需要缓慢亮起来, 如果是在配网的话就不用了。交给配网的代码进行控制
if ( g_net_breath_state = = NET_CFG_IDLE & & g_device_control . on = = true ) {
set_light ( DEV_POWER_ON , g_device_control . brightness_local , g_device_control . cct_local ) ;
}
set_switch ( g_device_control . on ) ; //按照当前值更新light
if ( ! g_device_control . is_networked & & ! g_device_control . is_net_configured ) {
try_detect_factory_test ( ) ;
}
@ -1272,7 +1388,9 @@ static void set_light2breathtimeout(void)
// 恢复到自定义模式
g_device_control . brightness_local = BRIGHTNESS_REMOTE2LOCAL ( NET_CFG_TIMEOUT_BRIGHTNESS ) ;
g_device_control . cct_local = CCT_REMOTE2LOCAL ( NET_CFG_TIMEOUT_CCT ) ;
calculate_pwm_duty ( ) ;
fade_ctx . current_brightness = g_device_control . brightness_local ;
fade_ctx . current_cct = g_device_control . cct_local ;
calculate_pwm_duty ( & g_device_control ) ;
update_pwm_output ( g_device_control . on , g_device_control . duty_cw , g_device_control . duty_ww ) ;
}
@ -1283,7 +1401,9 @@ static void set_light2net_cfg_done(void)
g_device_control . brightness_local = BRIGHTNESS_REMOTE2LOCAL ( NET_CFG_DEFAULT_BRIGHTNESS ) ;
g_device_control . cct_local = CCT_REMOTE2LOCAL ( NET_CFG_DEFAULT_CCT ) ;
g_device_control . fade_time = NET_CFG_DEFAULT_FADE_TIME ;
calculate_pwm_duty ( ) ;
fade_ctx . current_brightness = g_device_control . brightness_local ;
fade_ctx . current_cct = g_device_control . cct_local ;
calculate_pwm_duty ( & g_device_control ) ;
update_pwm_output ( g_device_control . on , g_device_control . duty_cw , g_device_control . duty_ww ) ;
}
@ -1292,7 +1412,6 @@ static void start_breath_timer(void)
{
g_net_breath_state = NET_CFG_BREATHING ;
g_net_cfg_start_time = uapi_systick_get_ms ( ) ;
breath_ctx . is_initial_breath = true ;
uapi_timer_start ( breath_ctx . timer_handle , breath_ctx . update_interval , breath_timer_callback , 0 ) ;
}