O7/Core/Src/yunhorn_sts_process.c

1788 lines
54 KiB
C
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/* USER CODE BEGIN Header */
/**
******************************************************************************
* @file yunhorn_sts_process.c *
* @author Yunhorn (r) Technology Limited Application Team *
* @brief Yunhorn (r) SmarToilets (r) Product configuration file. *
******************************************************************************
* @attention
*
* Copyright (c) 2022 Yunhorn Technology Limited.
* Copyright (c) 2022 Shenzhen Yunhorn Technology Co., Ltd.
* All rights reserved.
*
* This software is licensed under terms that can be found in the LICENSE file
* in the root directory of this software component.
* If no LICENSE file comes with this software, it is provided AS-IS.
*
******************************************************************************
*/
/* USER CODE END Header */
/* Includes ------------------------------------------------------------------*/
#include "stdint.h"
#include "platform.h"
#include "sys_conf.h"
#include "sys_app.h"
#include "stdio.h"
#include "stm32_systime.h"
#include "adc_if.h"
#include "gpio.h"
#include "LmHandler.h"
//#include "app_tof.h"
#include "lora_app.h"
#include "yunhorn_sts_prd_conf.h"
#include "yunhorn_sts_sensors.h"
#include "sts_cmox_hmac_sha.h"
/* USER CODE BEGIN Includes */
extern volatile sts_cfg_nvm_t sts_cfg_nvm;
extern volatile uint8_t sts_ac_code[20];
volatile uint8_t sts_work_mode = STS_UNI_MODE;
#if 0
#if defined(STS_O7)
volatile uint8_t sts_work_mode = STS_UNI_MODE;
#elif defined(STS_O6)
volatile uint8_t sts_work_mode = STS_DUAL_MODE;
#elif defined(STS_O2)
volatile uint8_t sts_work_mode = STS_RSS_MODE;
#endif
#endif
volatile uint8_t sts_service_mask=0;
volatile uint32_t rfac_timer;
volatile uint8_t sensor_data_ready=0;
volatile STS_PRESENCE_SENSOR_Event_Status_t sts_o7_event_status;
// GPIO reed hall pin
extern volatile uint8_t sts_reed_hall_result;
volatile uint8_t last_sts_reed_hall_result;
extern volatile uint8_t sts_hall1_read,sts_hall2_read, sts_hall3_read, sts_hall4_read;
volatile uint8_t sts_reed_hall_1_result=STS_Status_Door_Open,sts_reed_hall_2_result=STS_Status_SOS_Release, last_sts_reed_hall_1_result=STS_Status_Door_Open, last_sts_reed_hall_2_result=STS_Status_SOS_Release;
volatile uint8_t sts_reed_hall_3_result=STS_Status_Door_Open, last_sts_reed_hall_3_result=STS_Status_Door_Open, sts_reed_hall_4_result=STS_Status_Door_Open, last_sts_reed_hall_4_result=STS_Status_Door_Open;
volatile uint8_t sts_soap_level_state;
// RSS motion and distance
volatile STS_OO_SensorStatusDataTypeDef sts_o7_sensorData;
volatile uint16_t sts_distance_rss_distance=0, sts_sensor_install_height=0;//in mm
extern volatile float sts_presence_rss_distance, sts_presence_rss_score;
volatile uint8_t sts_rss_config_updated_flag = STS_RSS_CONFIG_NON;
extern volatile uint8_t sts_occupancy_overtime_state;
extern volatile distance_measure_cfg_t distance_cfg;
extern volatile uint16_t sts_fall_rising_pattern_factor1;
extern volatile uint16_t sts_roc_acc_standard_variance;
volatile uint32_t last_sts_rss_time_stamp=0;
// RSS fall detection
extern volatile uint8_t sts_fall_detection_acc_threshold, sts_fall_detection_depth_threshold, sts_occupancy_overtime_threshold_in_10min;
extern volatile uint8_t sts_fall_rising_detected_result, sts_fall_rising_detected_result_changed_flag;
extern volatile uint8_t sts_presence_fall_detection;
extern volatile uint8_t last_sts_fall_rising_detected_result;
extern volatile uint16_t sts_motionless_duration_threshold_in_min;
extern volatile uint8_t sts_status_color, sts_lamp_bar_color;//puColor
extern volatile uint8_t sts_cloud_netcolor; //netColor
extern uint8_t luminance_level;
SysTime_t mems_event_time;
volatile uint8_t sts_occupancy_status;
volatile uint8_t sts_hall1_changed_flag=0, sts_hall2_changed_flag=0, last_sts_hall1_result=0, last_sts_hall2_result=0;
volatile uint8_t sts_reed_hall_changed_flag = 0;
extern volatile uint8_t sts_reed_hall_result;
volatile uint8_t sts_water_leakage_result=0;
volatile uint8_t sts_water_leakage_changed_flag=0;
//extern volatile uint8_t sensor_data_ready;
#ifdef YUNHORN_STS_R4_ENABLED
volatile STS_R0_SensorDataTypeDef r4_data;
#endif
#ifdef YUNHORN_STS_O5_ENABLED
#endif
#if defined(STS_O7)||defined(STS_O6)
extern volatile uint8_t motion_detected_count;
extern volatile uint8_t motion_in_hs_zone[12][10]; //0.4*12=4.8meter high, past 10 measures
extern volatile uint8_t detected_hs_zone;
extern volatile STS_OO_RSS_SensorTuneDataTypeDef sts_presence_rss_config;
volatile uint32_t cnt=0;
volatile uint8_t sts_tof_result_changed_flag = 0;
volatile uint8_t sts_rss_result_changed_flag = 0;
volatile uint8_t sts_rss_result = STS_RESULT_NO_MOTION;
volatile uint8_t sts_rss_2nd_result = STS_RESULT_NO_MOTION; //2nd RSS sensor status
volatile uint8_t sts_tof_result = STS_RESULT_NO_MOTION;
volatile uint8_t last_sts_rss_result=STS_RESULT_NO_MOTION;
_Bool Motion_Flag = 0;
//extern volatile uint8_t last_sts_reed_hall_result;
extern volatile uint8_t last_lamp_bar_color;
extern volatile float sts_presence_rss_distance;
char sts_presence_fall_detection_message[10][20]={
"State_Normal",
"State_Fall_Down",
"State_Rising_Up",
"State_Laydown",
"State_Unconscious",
"State_StayStill",
"State_No_Movement"
};
#endif
/*
// UTIL_SEQ_SetTask((1 << CFG_SEQ_Task_YunhornSTSEventP4), CFG_SEQ_Prio_0);
// P1 --- REEDSWITCH, HALL ELEMENT, WATER LEAKAGE
// P2 --- SEE ABOVE, RSS PRESENCE
// P3 ----LAMP BAR SCOLLER PROCESS
// P4 --- TOF DISTANCE VL53L0X simple distance
// P5 --- TOF IN OUT COUNT VL53L3X in out or duration
// P6 --- SOAP Level, capacitive measurement
// P7 --- UltraSonic, 2nd wave UltraSonic range measure
// P8 --- AIR QUALITY AND ODOR LEVEL, SMOKING DETECTION
*/
/* USER CODE END Includes */
/* External variables ---------------------------------------------------------*/
/* USER CODE BEGIN EV */
/* USER CODE END EV */
/* Private typedef -----------------------------------------------------------*/
/* USER CODE BEGIN PTD */
/* USER CODE END PTD */
/* Private define ------------------------------------------------------------*/
/* USER CODE BEGIN PD */
/* USER CODE END PD */
/* Private macro -------------------------------------------------------------*/
/* USER CODE BEGIN PM */
/* USER CODE END PM */
/* Private variables ---------------------------------------------------------*/
/* USER CODE BEGIN PV */
/* USER CODE END PV */
/* Private function prototypes -----------------------------------------------*/
/* USER CODE BEGIN PFP */
#if (defined(YUNHORN_STS_O6_ENABLED) && defined(USE_ACCONEER_A111))
#endif
/* USER CODE END PFP */
/* Exported functions --------------------------------------------------------*/
#if 0
void STS_Sensor_Init(void)
{
/// **************************************************************************** TO-DO LIST
STS_REBOOT_CONFIG_Init();
UTIL_SEQ_RegTask((1 << CFG_SEQ_Task_YunhornSTSEventRFAC), UTIL_SEQ_RFU, STS_YunhornSTSEventRFAC_Process);
UTIL_SEQ_RegTask((1 << CFG_SEQ_Task_YunhornSTSEventP1), UTIL_SEQ_RFU, STS_YunhornSTSEventP1_Process);
UTIL_SEQ_RegTask((1 << CFG_SEQ_Task_YunhornSTSEventP2), UTIL_SEQ_RFU, STS_YunhornSTSEventP2_Process);
UTIL_SEQ_RegTask((1 << CFG_SEQ_Task_YunhornSTSEventP3), UTIL_SEQ_RFU, STS_YunhornSTSEventP3_Process);
#if 0
UTIL_SEQ_RegTask((1 << CFG_SEQ_Task_YunhornSTSEventP4), UTIL_SEQ_RFU, STS_YunhornSTSEventP4_Process);
UTIL_SEQ_RegTask((1 << CFG_SEQ_Task_YunhornSTSEventP5), UTIL_SEQ_RFU, STS_YunhornSTSEventP5_Process);
UTIL_SEQ_RegTask((1 << CFG_SEQ_Task_YunhornSTSEventP6), UTIL_SEQ_RFU, STS_YunhornSTSEventP6_Process);
UTIL_SEQ_RegTask((1 << CFG_SEQ_Task_YunhornSTSEventP7), UTIL_SEQ_RFU, STS_YunhornSTSEventP7_Process);
UTIL_SEQ_RegTask((1 << CFG_SEQ_Task_YunhornSTSEventP8), UTIL_SEQ_RFU, STS_YunhornSTSEventP8_Process);
#endif
#if defined(STS_O7)||defined(STS_O6)
UTIL_TIMER_Create(&YunhornSTSRSSWakeUpTimer, YUNHORN_STS_RSS_WAKEUP_CHECK_TIME, UTIL_TIMER_ONESHOT, OnYunhornSTSOORSSWakeUpTimerEvent, NULL);
UTIL_TIMER_Start(&YunhornSTSRSSWakeUpTimer);
UTIL_TIMER_Create(&YunhornSTSHeartBeatTimer, YUNHORN_STS_HEART_BEAT_CHECK_TIME, UTIL_TIMER_PERIODIC, OnYunhornSTSHeartBeatTimerEvent, NULL);
UTIL_TIMER_Start(&YunhornSTSHeartBeatTimer);
UTIL_TIMER_Start(&STSLampBarColorTimer);
//UTIL_TIMER_Start(&STSDurationCheckTimer);
#else
UTIL_TIMER_Create(&YunhornSTSSamplingCheckTimer, YUNHORN_STS_SAMPLING_CHECK_TIME, UTIL_TIMER_PERIODIC, OnYunhornSTSSamplingCheckTimerEvent, NULL);
UTIL_TIMER_Start(&YunhornSTSSamplingCheckTimer);
#endif
}
#endif
void STS_YunhornAuthenticationCode_Process(void)
{
if ((sts_ac_code[0] == 0x00) && (sts_ac_code[19]== 0x0)) {
APP_LOG(TS_OFF,VLEVEL_M, "Initial AC CODE blank... \r\n");
return;
}
sts_service_mask = (sts_hmac_verify()!= 0)? STS_SERVICE_MASK_L2:STS_SERVICE_MASK_L0;
if (sts_service_mask == STS_SERVICE_MASK_L2) {
sts_ac_code[0] = 0x0;
sts_ac_code[19]= 0x0;
}
APP_LOG(TS_OFF, VLEVEL_H, "STS_SERVICE_MASK:%d \r\n",sts_service_mask);
}
void STS_YunhornSTSEventRFAC_Process(void)
{
if ((sts_ac_code[0] ==0x0)&& (sts_ac_code[19]== 0x0))
{
if ((rfac_timer >= STS_BURN_IN_RFAC) && (rfac_timer < (STS_BURN_IN_RFAC +3)))
{
APP_LOG(TS_OFF, VLEVEL_M, "\r\n -------------------RFAC Process\r\n");
STS_SENSOR_Upload_Message(LORAWAN_USER_APP_CTRL_REPLY_PORT, 4, (uint8_t *)"RFAC");
}
if ((rfac_timer > (STS_BURN_IN_RFAC + 2)))
{
APP_LOG(TS_OFF, VLEVEL_M, "\r\n -------------------Verify RFAC Success or Not\r\n");
sts_service_mask = (sts_hmac_verify()!= 0)? STS_SERVICE_MASK_L2:STS_SERVICE_MASK_L0;
if (sts_service_mask == STS_SERVICE_MASK_L2) {
sts_ac_code[0] = 0x0;
sts_ac_code[19] = 0x0;
}
}
}
}
/*
* STS-P1 --- REEDSWITCH, HALL ELEMENT, WATER LEAKAGE
*/
void STS_YunhornSTSEventP1_Process(void)
{
sts_reed_hall_1_result = HALL1_STATE; //sts_hall1_read;
if (sts_reed_hall_1_result != last_sts_reed_hall_1_result)
{
sts_reed_hall_changed_flag |= 0x01;
}
last_sts_reed_hall_1_result = sts_reed_hall_1_result;
sts_reed_hall_2_result = HALL2_STATE;// sts_hall2_read;
if (sts_reed_hall_2_result != last_sts_reed_hall_2_result)
{
sts_reed_hall_changed_flag |= 0x02;
}
last_sts_reed_hall_2_result = sts_reed_hall_2_result;
sts_reed_hall_3_result = sts_hall3_read;//HALL3_STATE;// sts_hall3_read;
if (sts_reed_hall_3_result != last_sts_reed_hall_3_result)
{
sts_reed_hall_changed_flag |= 0x04;
}
last_sts_reed_hall_3_result = sts_reed_hall_3_result;
sts_reed_hall_4_result = sts_hall4_read;//HALL4_STATE;// sts_hall3_read;
if (sts_reed_hall_4_result != last_sts_reed_hall_4_result)
{
sts_reed_hall_changed_flag |= 0x08;
}
last_sts_reed_hall_4_result = sts_reed_hall_4_result;
STS_Combined_Status_Processing();
}
extern volatile uint32_t wcnt;
/*
* STS-P2 --- RSS PRESENCE
*/
void STS_YunhornSTSEventP2_Process(void)
{
//STS_Lamp_Bar_Refresh(); //TODO XXX eliminate refresh every second.... try
if ((sts_work_mode >= STS_RSS_MODE) && (sts_work_mode <= STS_TOF_RSS_MODE))
{
#if 0
switch (sts_work_mode) {
case STS_RSS_MODE:
sts_rss_config_updated_flag |= STS_RSS_CONFIG_DEFAULT;
break;
case STS_DUAL_MODE:
sts_rss_config_updated_flag |= STS_RSS_CONFIG_DEFAULT;
break;
case STS_UNI_MODE:
sts_rss_config_updated_flag |= STS_RSS_CONFIG_FALL_DETECTION;
break;
default:
break;
}
#endif
int res = sts_presence_rss_fall_rise_detection();
if (res == 0)
{
sts_rss_result_changed_flag = (sts_rss_result == last_sts_rss_result)? 0:1;
last_sts_rss_result = sts_rss_result;
//sts_fall_rising_detected_result_changed_flag = (sts_fall_rising_detected_result == last_sts_fall_rising_detected_result)?0:1;
//sts_fall_rising_detected_result_changed_flag = (sts_fall_rising_detected_result != last_sts_fall_rising_detected_result)?1:0;
last_sts_fall_rising_detected_result = sts_fall_rising_detected_result;
if (sts_service_mask > 0 ) {
sts_rss_result_changed_flag =0;
sts_reed_hall_changed_flag = 0;
sts_fall_rising_detected_result_changed_flag =0;
}
STS_Combined_Status_Processing();
} else APP_LOG(TS_OFF, VLEVEL_H, "\r\n RSS detection error =%d \r\n", res);
}
}
void STS_Reed_Hall_Presence_Detection(void)
{
// HAL_Delay(50); // BOUNCING ELIMIATION
sts_reed_hall_1_result = (sts_hall1_read==0)?STS_Status_Door_Close:STS_Status_Door_Open;
sts_reed_hall_2_result = (sts_hall2_read==0)?STS_Status_Door_Close:STS_Status_Door_Open;
sts_reed_hall_3_result = (sts_hall3_read==0)?STS_Status_Door_Close:STS_Status_Door_Open;
//sts_reed_hall_result = ((STS_Reed_Hall_State)&STS_Status_Door_Open);
// HAL_Delay(20); // BOUNCING ELIMIATION
sts_reed_hall_changed_flag = 0;
}
/*
* STS P3 process, Lamp Bar Scoller
*/
void STS_YunhornSTSEventP3_Process(void)
{
#if (defined(STS_O6) ||defined(STS_O7))
if (STS_Reed_Hall_State == STS_Status_Door_Open)
{
sts_lamp_bar_color =STS_GREEN;
}
else
{
sts_lamp_bar_color =STS_RED;
}
STS_Lamp_Bar_Scoller(sts_lamp_bar_color, luminance_level);
#endif
}
/*
* STS SOAP Level detection Process, STS_CAP_Sensor_Detection Process
* STS_CAP_SWITCH(ON) Boost Voltage to 5V, then hold for 1000 ms
* HAL_Delay(1000) (ms)
* STS_CAP_Read_Data() Read STS_CAP_DATA state
* STS_CAP_SWITCH(OFF) Switch Off Boosted Voltage
*/
/*
* STS-P4 Detection ToF distance (VL53L0X)
*
*/
void STS_YunhornSTSEventP4_Process(void)
{
PME_ON;
#ifdef LED_ONBOARD
LED_ON;
HAL_Delay(10);
LED_OFF;
#endif
#if defined(TOF_1)||defined(TOF_2)
APP_LOG(TS_OFF, VLEVEL_H, "\r\n TOF_1, TOF_2 RANGING Process\r\n");
STS_TOF_VL53L0X_Range_Process();
#endif
#ifdef TOF_3
APP_LOG(TS_OFF, VLEVEL_H, "\r\n TOF 3 RANGING Process ---- TOF250 Ranging \r\n");
STS_TOF250_Range_Process();
#endif
PME_OFF;
}
/*
* STS P5 Process, Detection ToF IN-OUT PEOPLE COUNT (VL53L3X)
*
*/
void STS_YunhornSTSEventP5_Process(void)
{
APP_LOG(TS_OFF, VLEVEL_L, "\r\n P5 Testing Process\r\n");
}
/*
* STS-P6 --- SOAP Level, capacitive measurement
* STS Soap Level Detection Process, STS_CAP_Sensor_Detection Process
* STS_CAP_SWITCH(ON) Boost Voltage to 5V, then hold for 1000 ms
* HAL_Delay(1000) (ms)
* STS_CAP_Read_Data() Read STS_CAP_DATA state
* STS_CAP_SWITCH(OFF) Switch Off Boosted Voltage
*/
void STS_YunhornSTSEventP6_Process(void)
{
APP_LOG(TS_OFF, VLEVEL_H, "\r\n P6 Testing Process\r\n");
PME_ON;
HAL_Delay(50);
#ifdef LED_ONBOARD
LED_ON;
HAL_Delay(20);
LED_OFF;
#endif
/* 1. Sensor Power On */
#if defined(SOAP_LEVEL_SENSOR)
HAL_GPIO_WritePin(SOAP_SWITCH_GPIO_Port, SOAP_SWITCH_Pin, GPIO_PIN_SET);
HAL_Delay(1000);
/* 2. Read sensor state */
sts_soap_level_state = HAL_GPIO_ReadPin(SOAP_STATUS_GPIO_Port,SOAP_STATUS_Pin);
APP_LOG(TS_OFF, VLEVEL_L, "\r\n Soap State = %s \r\n", (sts_soap_level_state==0x0)?" +++ Liquid Detected":" --- No Liquid");
HAL_GPIO_WritePin(SOAP_SWITCH_GPIO_Port, SOAP_SWITCH_Pin, GPIO_PIN_RESET);
if (sts_soap_level_state == 0x0)
{
#ifdef LED_ONBOARD
LED_ON;
HAL_Delay(20);
LED_OFF;
#endif
}
#endif
/* 3. Sensor Power Off */
PME_OFF;
}
/*
* STS P7 Process, Detection IAQ Sensors
* air quality and odor level sensors
*/
void STS_YunhornSTSEventP7_Process(void)
{
APP_LOG(TS_OFF, VLEVEL_L, "\r\n P7 Testing Process\r\n");
PME_ON;
PME_OFF;
}
/*
* STS P8 Process, Detection ETR Sensors, Water flow sensors, pulse counting
* PA5 sensors , TIM2_ETR, STS-M4
*/
void STS_YunhornSTSEventP8_Process(void)
{
APP_LOG(TS_OFF, VLEVEL_L, "\r\n P8 Testing Process\r\n");
}
/*
* STS P_IO_RS485 Process, Send Out Sensor Data Via RS485 interface
* sensors
*/
void STS_YunhornSTSEventPIORS485_Process(void)
{
APP_LOG(TS_OFF, VLEVEL_L, "\r\n P_IO_RS485 Process\r\n");
}
void STS_PRESENCE_SENSOR_WakeUp_Process_Sampling(void)
{
#if 0
if ((sensor_data_ready ==0)) {
STS_PRESENCE_SENSOR_GetValue();
}
#endif
}
void STS_PRESENCE_SENSOR_After_Wake_Up()
{
}
void STS_FallDetection_LampBarProcess(void)
{
}
void STS_YunhornSTSFallDetection(void)
{
//APP_LOG(TS_OFF, VLEVEL_M, "\r\n YUNHORN STS FALL DETECTION \r\n");
//STS_YunhornCheckStandardDeviation();
}
void STS_Combined_Status_Processing(void)
{
switch (sts_work_mode)
{
case STS_NETWORK_MODE:
sts_status_color = sts_cloud_netcolor;
sts_lamp_bar_color = sts_cloud_netcolor;
break;
case STS_WIRED_MODE: // NO LAMP BAR FOR THOSE WATER LEAKAGE SENSOR OR SOAP CAPACITY SENSORS
sts_status_color = STS_DARK;
#ifdef STS_M1
sts_water_leakage_result = (sts_reed_hall_result == STS_Status_Door_Open )?STS_RESULT_WATER_LEAKAGE_YES:STS_RESULT_WATER_LEAKAGE_NO;
sts_water_leakage_changed_flag = 1;
#endif
break;
case STS_REEDSWITCH_MODE:
sts_status_color = (sts_reed_hall_1_result == STS_Status_Door_Open )? STS_GREEN: STS_RED;
if (sts_reed_hall_2_result == STS_Status_SOS_Pushdown )
{
sts_status_color = STS_RED_BLUE;
}
break;
case STS_RSS_MODE:
if (sts_rss_result == STS_RESULT_NO_MOTION){
sts_status_color = STS_GREEN;
} else if ((sts_rss_result == STS_RESULT_MOTION))
{
sts_status_color = STS_RED;
}
break;
case STS_DUAL_MODE: // FOR STS_O6
if ((sts_rss_result == STS_RESULT_NO_MOTION) && (sts_reed_hall_1_result == STS_Status_Door_Open )&& (sts_reed_hall_2_result == STS_Status_SOS_Release ))
{
sts_status_color = STS_GREEN;
} else if ((sts_rss_result == STS_RESULT_MOTION) || (sts_reed_hall_1_result == STS_Status_Door_Close )||(sts_reed_hall_2_result == STS_Status_SOS_Pushdown ))
{
sts_status_color = STS_RED;
if (sts_reed_hall_2_result == STS_Status_SOS_Pushdown )
{
sts_status_color = STS_RED_BLUE;
}
}
break;
case STS_UNI_MODE: //FOR STS-O7
if ((sts_rss_result == STS_RESULT_NO_MOTION) && (sts_reed_hall_1_result == STS_Status_Door_Open )&& (sts_reed_hall_2_result == STS_Status_SOS_Release )
&& (sts_reed_hall_3_result == STS_Status_Alarm_Mute_Release )&& (sts_reed_hall_4_result == STS_Status_Alarm_Reset_Release ))
{
sts_status_color = STS_GREEN;
} else if ((sts_rss_result == STS_RESULT_MOTION) || (sts_reed_hall_1_result == STS_Status_Door_Close )||(sts_reed_hall_2_result == STS_Status_SOS_Pushdown )
|| (sts_reed_hall_3_result == STS_Status_Alarm_Mute_Pushdown )|| (sts_reed_hall_4_result == STS_Status_Alarm_Reset_Pushdown ))
{
sts_status_color = STS_RED;
if (sts_reed_hall_2_result == STS_Status_SOS_Pushdown )
{
sts_status_color = STS_RED_BLUE;
}
}
switch(sts_fall_rising_detected_result)
{
case STS_PRESENCE_NORMAL:
//do nothing
break;
case STS_PRESENCE_LAYDOWN:
sts_lamp_bar_color = STS_YELLOW;
sts_status_color = STS_YELLOW;
break;
case STS_PRESENCE_FALL: //RED_BLUE FLASH
sts_lamp_bar_color = STS_RED_BLUE;
sts_status_color = STS_RED_BLUE;
break;
case STS_PRESENCE_RISING: //NORMAL OCCUPANCY STATUS
sts_lamp_bar_color = STS_RED;
sts_status_color = STS_RED;
break;
default:
// sts_lamp_bar_color = STS_RED;
// sts_status_color = STS_RED;
break;
}
break;
case STS_REMOTE_REED_RSS_MODE:
if ((sts_rss_result == STS_RESULT_NO_MOTION) && (sts_reed_hall_result == STS_Status_Door_Open ))
{
sts_status_color = STS_GREEN;
} else if ((sts_rss_result == STS_RESULT_MOTION) || (sts_reed_hall_result == STS_Status_Door_Close ))
{
sts_status_color = STS_RED;
}
break;
case STS_DUAL_RSS_MODE:
if ((sts_rss_result == STS_RESULT_NO_MOTION) && (sts_rss_2nd_result == STS_RESULT_NO_MOTION))
{
sts_status_color = STS_GREEN;
} else if ((sts_rss_result == STS_RESULT_MOTION) || (sts_rss_2nd_result == STS_RESULT_MOTION))
{
sts_status_color = STS_RED;
}
break;
case STS_TOF_RSS_MODE:
if ((sts_rss_result == STS_RESULT_NO_MOTION) && (sts_tof_result == STS_RESULT_NO_PRESENCE)){
sts_status_color = STS_GREEN;
} else if ((sts_rss_result == STS_RESULT_MOTION) || (sts_tof_result == STS_RESULT_PRESENCE))
{
sts_status_color = STS_RED;
}
break;
// TO-DO LIST ***********************************************************
case STS_TOF_DISTANCE_MODE:
if ((sts_tof_result == STS_RESULT_NO_PRESENCE)) {
sts_status_color = STS_GREEN;
} else if ((sts_tof_result == STS_RESULT_PRESENCE)) {
sts_status_color = STS_RED;
}
break;
case STS_TOF_PRESENCE_MODE:
if ((sts_tof_result == STS_RESULT_NO_PRESENCE)) {
sts_status_color = STS_GREEN;
} else if ((sts_tof_result == STS_RESULT_PRESENCE)) {
sts_status_color = STS_RED;
}
break;
case STS_TOF_IN_OUT_MODE:
if ((sts_tof_result == STS_RESULT_NO_PRESENCE)) {
sts_status_color = STS_GREEN;
} else if ((sts_tof_result == STS_RESULT_PRESENCE)) {
sts_status_color = STS_RED;
}
break;
// TO-DO LIST ***********************************************************
default:
break;
}
if ((sts_work_mode == STS_WIRED_MODE) || (sts_service_mask > STS_SERVICE_MASK_L0))
{
sts_status_color = STS_DARK;
sts_lamp_bar_color = STS_DARK;
last_lamp_bar_color = STS_DARK;
STS_Lamp_Bar_Set_Dark();
}
else
{
if ((last_lamp_bar_color != sts_status_color))
{
sts_lamp_bar_color = sts_status_color;
//STS_Lamp_Bar_Set_STS_RGB_Color(sts_lamp_bar_color, luminance_level);
last_lamp_bar_color = sts_lamp_bar_color;
}
}
if ((sts_rss_result_changed_flag)|| (sts_reed_hall_changed_flag)||(sts_fall_rising_detected_result_changed_flag))
{
//sts_rss_result_changed_flag =0;
//sts_reed_hall_changed_flag =0;
//sts_fall_rising_detected_result_changed_flag =0;
//sts_tof_result_changed_flag =0;
sensor_data_ready = 1;
//STS_PRESENCE_SENSOR_Prepare_Send_Data();
}
}
void STS_PRESENCE_SENSOR_NVM_CFG(void)
{
sts_presence_rss_config.default_start_m = (float)((float)sts_cfg_nvm.p[RSS_CFG_START_M]*0.1f);
sts_presence_rss_config.default_length_m = (float)((float)sts_cfg_nvm.p[RSS_CFG_LENGTH_M]*0.1f);
sts_presence_rss_config.default_threshold = (float)((float)sts_cfg_nvm.p[RSS_CFG_THRESHOLD]*0.1f);
sts_presence_rss_config.default_receiver_gain = (float)((float)sts_cfg_nvm.p[RSS_CFG_RECEIVER_GAIN]*0.01f);
sts_presence_rss_config.default_zone_length_m = DEFAULT_ZONE_LENGTH;
sts_presence_rss_config.default_profile = (float)(sts_cfg_nvm.p[RSS_CFG_PROFILE]);
sts_presence_rss_config.default_update_rate_tracking = (float)(sts_cfg_nvm.p[RSS_CFG_RATE_TRACKING]);
sts_presence_rss_config.default_update_rate_presence = (float)(sts_cfg_nvm.p[RSS_CFG_RATE_PRESENCE]);
sts_presence_rss_config.default_hwaas = (float)(sts_cfg_nvm.p[RSS_CFG_HWAAS]);
sts_presence_rss_config.default_nbr_removed_pc = (float)(sts_cfg_nvm.p[RSS_CFG_NBR_REMOVED_PC]);
//filter parameter
sts_presence_rss_config.default_inter_frame_deviation_time_const = (float)(sts_cfg_nvm.p[RSS_CFG_ITE_DEVIATION]*0.1f);
sts_presence_rss_config.default_inter_frame_fast_cutoff = (float)(sts_cfg_nvm.p[RSS_CFG_ITE_FAST_CUTOFF]);
sts_presence_rss_config.default_inter_frame_slow_cutoff = (float)(sts_cfg_nvm.p[RSS_CFG_ITE_SLOW_CUTOFF]*0.01f);
sts_presence_rss_config.default_intra_frame_time_const = (float)(sts_cfg_nvm.p[RSS_CFG_ITR_TIME]);
sts_presence_rss_config.default_intra_frame_weight = (float)(sts_cfg_nvm.p[RSS_CFG_ITR_WEIGHT]*0.1f);
sts_presence_rss_config.default_output_time_const = (float)(sts_cfg_nvm.p[RSS_CFG_OUTPUT_TIME]*0.1f);
//filter parameter
sts_presence_rss_config.default_downsampling_factor = (float)(sts_cfg_nvm.p[RSS_CFG_DOWNSAMPLING_FACTOR]);
sts_presence_rss_config.default_power_save_mode = (float)(sts_cfg_nvm.p[RSS_CFG_POWER_MODE]);
// sts_rss_config_updated_flag = (sts_rss_config_updated_flag|STS_RSS_CONFIG_FULL); //set to 2 for FULL config effect in next detection
//sts_rss_config_updated_flag = (STS_RSS_CONFIG_FULL); //set to 2 for FULL config effect in next detection
//sts_presence_rss_config.default_config_update_flag = (uint8_t) sts_rss_config_updated_flag;
sts_rss_config_updated_flag = (uint8_t)(sts_cfg_nvm.p[RSS_CFG_UPDATE_FLAG]);
APP_LOG(TS_ON, VLEVEL_H, "\r\n##### Reboot --- with NVM CFG'ED RSS flag =%02x \r\n", sts_rss_config_updated_flag);
}
void STS_PRESENCE_SENSOR_NVM_CFG_SIMPLE(void)
{
sts_presence_rss_config.default_start_m = (float)(sts_cfg_nvm.p[RSS_CFG_START_M]*0.1f);
sts_presence_rss_config.default_length_m = (float)(sts_cfg_nvm.p[RSS_CFG_LENGTH_M]*0.1f);
sts_presence_rss_config.default_threshold = (float)(sts_cfg_nvm.p[RSS_CFG_THRESHOLD]*0.1f);
sts_presence_rss_config.default_receiver_gain = (float)(sts_cfg_nvm.p[RSS_CFG_RECEIVER_GAIN]*0.01f);
sts_presence_rss_config.default_zone_length_m = DEFAULT_ZONE_LENGTH;
sts_presence_rss_config.default_profile = (float)(sts_cfg_nvm.p[RSS_CFG_PROFILE]);
sts_presence_rss_config.default_update_rate_tracking = (float)(sts_cfg_nvm.p[RSS_CFG_RATE_TRACKING]);
sts_presence_rss_config.default_update_rate_presence = (float)(sts_cfg_nvm.p[RSS_CFG_RATE_PRESENCE]);
sts_presence_rss_config.default_hwaas = (float)(sts_cfg_nvm.p[RSS_CFG_HWAAS]);
sts_presence_rss_config.default_nbr_removed_pc = (float)(sts_cfg_nvm.p[RSS_CFG_NBR_REMOVED_PC]);
// sts_rss_config_updated_flag = (sts_rss_config_updated_flag|STS_RSS_CONFIG_SIMPLE); //set to 1 for simple config effect in next detection
sts_rss_config_updated_flag = (STS_RSS_CONFIG_SIMPLE); //set to 1 for simple config effect in next detection
//sts_presence_rss_config.default_config_update_flag = (uint8_t) sts_rss_config_updated_flag;
sts_rss_config_updated_flag = (uint8_t)(sts_cfg_nvm.p[RSS_CFG_UPDATE_FLAG]);
}
void STS_PRESENCE_SENSOR_Init_Send_Data(void)
{
//sts_o7_sensorData.lamp_bar_color = STS_GREEN;
sts_o7_sensorData.workmode = sts_work_mode; //STS_DUAL_MODE;
sts_o7_sensorData.state_sensor1_on_off = 0x0;
sts_o7_sensorData.state_sensor2_on_off = 0x0;
sts_o7_sensorData.state_sensor3_on_off = 0x0;
sts_o7_sensorData.state_sensor4_on_off = 0x0;
sts_o7_sensorData.rss_presence_distance = 0x0;
sts_o7_sensorData.rss_presence_score = 0x0;
sts_o7_sensorData.fall_state = STS_PRESENCE_NORMAL;
sts_o7_sensorData.fall_speed = 0x0;
sts_o7_sensorData.fall_gravity = 0x0;
sts_o7_sensorData.over_stay_state = 0x0;
sts_o7_sensorData.over_stay_duration = 0x0;
sts_o7_sensorData.unconscious_state = 0x0;
sts_o7_sensorData.no_movement_state = 0x0;
sts_o7_sensorData.unconscious_duration = 0x0;
sts_o7_sensorData.no_movement_duration = 0x0;
sts_o7_sensorData.event_sensor1_start_time = 0x0;
sts_o7_sensorData.event_sensor1_duration = 0x0;
sts_o7_sensorData.event_sensor2_start_time = 0x0;
sts_o7_sensorData.event_sensor2_duration = 0x0;
sts_o7_sensorData.event_sensor2_start_timestamp = 0x0;
sts_o7_sensorData.event_sensor2_stop_timestamp = 0x0;
sts_o7_sensorData.event_sensor3_motion_start_time = 0x0;
sts_o7_sensorData.event_sensor3_motion_duration = 0x0;
sts_o7_sensorData.event_sensor3_fall_start_time = 0x0;
sts_o7_sensorData.event_sensor3_fall_start_time_stamp = 0x0;
sts_o7_sensorData.event_sensor3_fall_duration = 0x0;
sts_o7_sensorData.event_sensor3_fall_stop_time_stamp = 0x0;
sts_o7_sensorData.event_sensor4_start_time = 0x0;
sts_o7_sensorData.event_sensor4_duration = 0x0;
sts_o7_sensorData.event_sensor3_fall_distance = 0x0;
sts_o7_sensorData.event_sensor3_fall_motionscore = 0x0;
sts_o7_sensorData.battery_Pct = 99; // 99% as init value
sts_o7_sensorData.dutycycletimelevel = 1;
sensor_data_ready = 0;
}
void STS_PRESENCE_SENSOR_Prepare_Send_Data(STS_OO_SensorStatusDataTypeDef *sensor_data)
{
sensor_data->lamp_bar_color = sts_lamp_bar_color;
sensor_data->workmode = sts_work_mode;
// #1 for HALL_ELEMENT, DOOR CONTACT, SENSOR STATE PROCESS
sensor_data->state_sensor1_on_off = HALL1_STATE;//sts_hall1_read; //sts_hsts_reed_hall_result; // sts_hall1_read
sensor_data->state_sensor2_on_off = HALL2_STATE;//sts_hall2_read; //sts_emergency_button_pushed; //sts_hall2_read
sensor_data->state_sensor3_on_off = sts_rss_result;
sensor_data->state_sensor4_on_off = sts_hall3_read; //for alarm mute button
sensor_data->state_sensor5_on_off = sts_hall4_read; //for alarm reset button
if (sensor_data->state_sensor2_on_off==STS_Status_SOS_Pushdown)
{
sensor_data->event_sensor2_start_timestamp = sts_o7_sensorData.event_sensor2_start_timestamp;
sensor_data->event_sensor2_stop_timestamp = sts_o7_sensorData.event_sensor2_stop_timestamp;
sts_o7_sensorData.event_sensor2_start_timestamp = 0;
} else {
sensor_data->event_sensor2_start_timestamp = 0;
sensor_data->event_sensor2_stop_timestamp = 0;
sensor_data->event_sensor2_stop_timestamp = sts_o7_sensorData.event_sensor2_stop_timestamp;
sts_o7_sensorData.event_sensor2_stop_timestamp = 0;
}
// #2 for MOTION RELATED SENSOR STATE PROCESS, OCCUPY/VACANT/OVERSTAY/LONGSTAY/UNCONSCIOUS
if (sts_rss_result == STS_RESULT_MOTION)
{
sensor_data->rss_presence_distance = (uint16_t)(sts_presence_rss_distance);
sensor_data->rss_presence_score = (uint16_t)(sts_presence_rss_score);
// uint8_t sts_unconscious_state;
// uint16_t sts_unconscious_threshold, sts_unconscious_threshold_duration;
}
else {
sensor_data->rss_presence_distance = 0x0;
sensor_data->rss_presence_score = 0x0;
}
// no_movement or unconscious duration
sensor_data->unconscious_state = ((sts_fall_rising_detected_result == STS_PRESENCE_UNCONSCIOUS) ||
(sts_fall_rising_detected_result==STS_PRESENCE_STAYSTILL) ||
(sts_fall_rising_detected_result==STS_PRESENCE_NO_MOVEMENT))? 1:0;
sensor_data->unconscious_duration = sts_o7_sensorData.event_sensor3_unconcious_duration;
sensor_data->no_movement_state = sensor_data->unconscious_state;
sensor_data->no_movement_duration = sts_o7_sensorData.event_sensor3_no_movement_duration;
if (sensor_data->unconscious_state !=0)
{
APP_LOG(TS_OFF,VLEVEL_M,"\r\n ... Unconscious or No Movement Duration = %u Sec [Threshold: %u Seconds]\r\n",
sensor_data->unconscious_duration, sts_motionless_duration_threshold_in_min*60);
}
// Over stay, long stay duration and state
sensor_data->over_stay_state = sts_o7_sensorData.over_stay_state;
sensor_data->over_stay_duration = sts_o7_sensorData.event_sensor1_duration;
if (sensor_data->over_stay_state !=0)
{
APP_LOG(TS_OFF,VLEVEL_M,"\r\n ... Over Stay Duration = %u Sec [Threshold: %u Seconds]\r\n",
sensor_data->over_stay_duration,
sts_occupancy_overtime_threshold_in_10min*60);
}
// #3 for FALL DETECTION, FALL, RISING, LAYDOWN DURATION CONFIRMATION STATE PROCESS
sensor_data->fall_state = sts_fall_rising_detected_result;
if ((sts_fall_rising_detected_result == STS_PRESENCE_FALL)||
(sts_fall_rising_detected_result == STS_PRESENCE_RISING)||
(sts_fall_rising_detected_result == STS_PRESENCE_LAYDOWN))
{
APP_LOG(TS_OFF, VLEVEL_M, "\r\n......FALL RISING DETECTION RESULT: %25s \r\n",
(char*)sts_presence_fall_detection_message[sts_fall_rising_detected_result] );
sensor_data->fall_speed = (uint8_t)sts_fall_rising_pattern_factor1;
sensor_data->fall_gravity = (uint8_t)sts_roc_acc_standard_variance;
sensor_data->event_sensor3_fall_start_time_stamp = sts_o7_sensorData.event_sensor3_fall_start_time_stamp;
sensor_data->event_sensor3_fall_stop_time_stamp = sts_o7_sensorData.event_sensor3_fall_stop_time_stamp;
sensor_data->event_sensor3_fall_distance = (uint16_t)(sts_o7_sensorData.event_sensor3_fall_distance);
sensor_data->event_sensor3_fall_motionscore = (uint16_t)(sts_o7_sensorData.event_sensor3_fall_motionscore);
} else {
sensor_data->fall_speed = 0;
sensor_data->fall_gravity = 0;
sensor_data->event_sensor3_fall_start_time_stamp = 0;
sensor_data->event_sensor3_fall_stop_time_stamp =0;
}
#if 0
// TODO XXXX
// FOR ALARM MUTE AND RESET
if ((sts_occupancy_overtime_threshold_in_10min != 0) && (event_start_time !=0))
{
if (sts_occupancy_overtime_state == 1U) {
sts_status_color = STS_RED_BLUE;
sts_lamp_bar_color = STS_RED_BLUE;
}
//STS_Lamp_Bar_Refresh();
}
#endif
sensor_data_ready = 1;
}
/**
* @brief Initializes the motion sensors
* @param Instance Motion sensor instance
* @param Functions Motion sensor functions. Could be :
* - MOTION_ACCELERO for instance
* @retval BSP status
*/
void STS_PRESENCE_SENSOR_Init(void)
{
APP_LOG(TS_ON, VLEVEL_H, "##### YunHorn SmarToilets(r) Presence Sensor Started\r\n");
sts_o7_sensorData.workmode = (uint8_t)sts_work_mode; //STS_DUAL_MODE;
sts_o7_sensorData.lamp_bar_color = (uint8_t)STS_GREEN;
sts_o7_sensorData.battery_Pct = 99;
sts_o7_sensorData.dutycycletimelevel = 1;
sts_o7_sensorData.event_sensor1_start_time = 0;
sts_o7_sensorData.event_sensor1_stop_time = 0;
sts_o7_sensorData.event_sensor1_duration = 0;
sts_o7_sensorData.event_sensor2_start_time = 0;
sts_o7_sensorData.event_sensor2_stop_time = 0;
sts_o7_sensorData.event_sensor2_duration = 0;
sts_o7_sensorData.event_sensor2_start_timestamp = 0;
sts_o7_sensorData.event_sensor2_stop_timestamp = 0;
sts_o7_sensorData.event_sensor3_motion_start_time = 0;
sts_o7_sensorData.event_sensor3_motion_stop_time = 0;
sts_o7_sensorData.event_sensor3_motion_duration = 0;
sts_o7_sensorData.event_sensor3_fall_start_time = 0;
sts_o7_sensorData.event_sensor3_fall_start_time_stamp = 0;
sts_o7_sensorData.event_sensor3_fall_stop_time = 0;
sts_o7_sensorData.event_sensor3_fall_stop_time_stamp = 0;
sts_o7_sensorData.event_sensor3_fall_duration = 0;
sts_o7_sensorData.event_sensor4_start_time = 0;
sts_o7_sensorData.event_sensor4_stop_time = 0;
sts_o7_sensorData.event_sensor4_duration = 0;
sts_o7_sensorData.over_stay_state = 0;
sts_o7_sensorData.over_stay_duration = 0;
sts_o7_sensorData.no_movement_state = 0;
sts_o7_sensorData.no_movement_duration = 0;
sts_o7_sensorData.unconscious_state = 0;
sts_o7_sensorData.unconscious_duration = 0;
//PME_ON;
//STS_PRESENCE_SENSOR_REEDSWITCH_HALL_Init();
//STS_PRESENCE_SENSOR_TOF_Init();
//HAL_Delay(2000);
//STS_PRESENCE_SENSOR_Distance_Measure_Process();
}
void STS_PRESENCE_SENSOR_TOF_Init(void)
{
APP_LOG(TS_ON, VLEVEL_H, "##### YunHorn SmarToilets(r) MEMS TOF Initializing \r\n");
}
void STS_PRESENCE_SENSOR_REEDSWITCH_HALL_Init(void)
{
APP_LOG(TS_ON, VLEVEL_H, "##### YunHorn SmarToilets(r) REED SWITCH HALL ELEMENT Initializing \r\n");
}
#if 0
void STS_PRESENCE_SENSOR_RSS_Init(void)
{
APP_LOG(TS_ON, VLEVEL_H, "##### YunHorn SmarToilets(r) MEMS RSS Initializing \r\n");
// PME_ON;
#if 0
//if ((sts_distance_rss_distance==0)&&(sts_sensor_install_height==0))
{
uint8_t exit_status =0;
do {
exit_status=sts_distance_rss_detector_distance();
if (exit_status ==0) {
APP_LOG(TS_ON, VLEVEL_M, "##### RSS Installation Height =%u \r\n", (uint16_t)sts_distance_rss_distance);
}
else {
APP_LOG(TS_ON, VLEVEL_M, "##### RSS Installation Height Error \r\n");
//HAL_Delay(100);
}
} while((0));
sts_sensor_install_height = (uint16_t)sts_distance_rss_distance;
}
#endif
STS_PRESENCE_SENSOR_NVM_CFG();
#if 0
switch (sts_work_mode)
{
case STS_RSS_MODE:
sts_rss_config_updated_flag |= STS_RSS_CONFIG_DEFAULT;
break;
case STS_DUAL_MODE:
sts_rss_config_updated_flag |= STS_RSS_CONFIG_DEFAULT;
break;
case STS_UNI_MODE:
sts_rss_config_updated_flag |= STS_RSS_CONFIG_FALL_DETECTION;
break;
default:
break;
}
#endif
APP_LOG(TS_ON, VLEVEL_M, "\r\n##### Reboot --- with NVM CFG'ED RSS flag =%02x \r\n", sts_rss_config_updated_flag);
}
#endif
void STS_PRESENCE_SENSOR_Distance_Measure_Process(void)
{
uint8_t exit_status = EXIT_SUCCESS, i=0;
APP_LOG(TS_OFF, VLEVEL_M, "\r\n ****start_m=%u length_m=%u profile=%u hwaas=%u \r\n",
(unsigned int)(distance_cfg.start_m*1000),(unsigned int)(distance_cfg.length_m*1000),
(unsigned int)(distance_cfg.acc_profile),(unsigned int)(distance_cfg.hwaas));
do
{
LED1_TOGGLE;
exit_status = sts_distance_rss_detector_distance();
HAL_Delay(10);
i++;
} while ((exit_status == EXIT_FAILURE) && (i < 1));
LED1_ON;
}
void STS_PRESENCE_SENSOR_Background_Measure_Process(uint16_t *bg_distance, uint16_t *bg_motion_noise)
{
uint8_t previous_sts_work_mode = sts_work_mode, previous_sts_lamp_bar_color = sts_lamp_bar_color;
uint16_t distance_center=0, motion_noise=0;
sts_work_mode = STS_RSS_BACKGROUND_MODE;
sts_lamp_bar_color = STS_BLUE;
APP_LOG(TS_OFF, VLEVEL_M, "\r\n SCAN Background Noise ... \r\n");
sts_presence_rss_background_evaluation_process(&distance_center, &motion_noise);
APP_LOG(TS_OFF, VLEVEL_H, "\r\n Background Distance center at %d mm, and Motion Noise =%d \r\n", distance_center, motion_noise);
*bg_distance = distance_center;
*bg_motion_noise = motion_noise;
sts_work_mode = previous_sts_work_mode;
sts_lamp_bar_color = previous_sts_lamp_bar_color;
}
void STS_PRESENCE_SENSOR_Function_Test_Process(uint8_t *self_test_result, uint8_t count)
{
uint8_t bring_up_result[16];
uint8_t previous_lamp_bar_color=sts_lamp_bar_color;
uint16_t bg_range=0, bg_noise=0;
PME_ON;
HAL_Init();
MX_GPIO_Init();
HAL_Delay(150); //wait for sensor ready
for (uint8_t i=0;i < count; i++) //while(1)
{
STS_Lamp_Bar_Self_Test_Simple();
STS_Lamp_Bar_Refresh();
HAL_Delay(200);
sts_lamp_bar_color = STS_PINK;
sts_presence_rss_bring_up_test(bring_up_result);
HAL_Delay(200);
sts_lamp_bar_color = STS_CYAN;
STS_PRESENCE_SENSOR_Distance_Measure_Process();
bring_up_result[10]=sts_sensor_install_height>>8&0xff;
bring_up_result[11]=sts_sensor_install_height&0xff;
HAL_Delay(200);
STS_PRESENCE_SENSOR_Background_Measure_Process(&bg_range, &bg_noise);
bring_up_result[12]=bg_range>>8&0xff;
bring_up_result[13]=bg_range&0xff;
bring_up_result[14]=bg_noise>>8&0xff;
bring_up_result[15]=bg_noise&0xff;
}
HAL_Delay(200);
sts_lamp_bar_color = previous_lamp_bar_color;
UTIL_MEM_cpy_8(self_test_result, bring_up_result, sizeof(bring_up_result));
}
uint8_t STS_SENSOR_MEMS_Get_ID(uint8_t *devID)
{
uint8_t scanned_id[2] = {0x0,0x0};
#if defined(STS_O7)||defined(STS_O6)
if (hal_test_spi_read_chipid(scanned_id))
{
devID[0] = scanned_id[0];
devID[1] = scanned_id[1];
APP_LOG(TS_OFF, VLEVEL_H,"\r\n--------------devID = %02x %02x \r\n",devID[0], devID[1]);
return true;
}
else
{
return false;
}
#endif
}
#ifdef STS_R4
void YUNHORN_STS_R4_SENSOR_Read(STS_R0_SensorDataTypeDef *r4_data)
{
#ifdef SOAP_LEVEL_SENSOR
r4_data->on_off_event = (sts_soap_level_state==0x0)? 1:0;
r4_data->measure_tech = 0x0; // capacity measure
#endif
sensor_data_ready = 0x1;
}
void YUNHORN_STS_R4_SENSOR_Init(void)
{
r4_data.on_off_event = 0x0;
r4_data.measure_tech = 0x0;
sensor_data_ready = 0x0;
}
#endif
#if defined(YUNHORN_STS_R4_ENABLED)
void STS_R0_SENSOR_Read(STS_R0_SensorDataTypeDef *r0_data)
{
#ifdef SOAP_LEVEL_SENSOR
r0_data->on_off_event = sts_soap_level_state;
r0_data->measure_tech = 0; /* 0: capacit, 1:dTof, 2: ultrasonic */
#elif defined(TOF_1)||defined(TOF_2)||defined(TOF_3)
r0_data->measure_tech = 1; /* 0: capacit, 1:dTof, 2: ultrasonic */
r0_data->distance_mm = sts_tof_distance_data[0];
r0_data->distance1_mm = sts_tof_distance_data[1];
r0_data->distance2_mm = sts_tof_distance_data[2];
#elif defined(ROCTEC_R5)
r0_data->distance1_mm = sts_tof_distance_data[0]+sts_tof_distance_data[1]+sts_tof_distance_data[2];
#endif
sensor_data_ready = 1;
}
#endif
void STS_SENSOR_NVM_CFG(void)
{
}
void STS_SENSOR_NVM_CFG_SIMPLE(void)
{
}
#if defined(YUNHORN_STS_O5_ENABLED)
void STS_O5_SENSOR_Read(STS_OO_SensorDataTypeDef *oo_data)
{
oo_data->state_sensor1_on_off = sts_reed_hall_result;
sensor_data_ready = 1;
}
#endif
/* reedswitch 1 on off */
void OnSensor1StateChanged(void)
{
SysTime_t sensor_event_time = SysTimeGetMcuTime();
if (sts_hall1_read == STS_Status_Door_Close)
{
sts_o7_sensorData.event_sensor1_start_time = sensor_event_time.Seconds;
sts_o7_sensorData.event_sensor1_duration = 0;
APP_LOG(TS_OFF, VLEVEL_L, "Door Closed ---Timer start: %u\r\n",sts_o7_sensorData.event_sensor1_start_time );
} else if (sts_hall1_read==STS_Status_Door_Open)
{
sts_o7_sensorData.event_sensor1_start_time = 0;
sts_o7_sensorData.event_sensor1_stop_time = sensor_event_time.Seconds;
//sts_o7_sensorData.event_sensor1_duration = 0;
sts_o7_sensorData.over_stay_state = 0;
}
}
/* SOS emergency button on off */
void OnSensor2StateChanged(void)
{
SysTime_t sensor_event_time = SysTimeGetMcuTime();
uint32_t time_stamp=STS_Get_Date_Time_Stamp();
if (sts_hall2_read==STS_Status_SOS_Pushdown)
{
sts_o7_sensorData.event_sensor2_start_time = sensor_event_time.Seconds;
sts_o7_sensorData.event_sensor2_start_timestamp = time_stamp;
sts_o7_sensorData.event_sensor2_stop_time = 0;
sts_o7_sensorData.event_sensor2_duration = 0;
APP_LOG(TS_OFF, VLEVEL_L, "SOS PushDown ---Timer start: %u\r\n",sts_o7_sensorData.event_sensor2_start_time );
}else if (sts_hall2_read==STS_Status_SOS_Release)
{
sts_o7_sensorData.event_sensor2_start_time = 0;
sts_o7_sensorData.event_sensor2_start_timestamp = 0;
sts_o7_sensorData.event_sensor2_stop_time = sensor_event_time.Seconds;
sts_o7_sensorData.event_sensor2_stop_timestamp = time_stamp;
//sts_o7_sensorData.over_stay_state = 0;
//sts_o7_sensorData.event_sensor2_duration = 0;
}
}
/* motion sensor RSS ON-OFF */
void OnSensorRSS3StateChanged(void)
{
SysTime_t sensor_event_time = SysTimeGetMcuTime();
#if 0
if ((sensor_event_time.Seconds - last_sts_rss_time_stamp) < 3 ) //less than 3 seconds ... return for flipping filter
{
return ;
}
#endif
if (sts_rss_result == STS_RESULT_MOTION)
{
sts_o7_sensorData.event_sensor3_motion_start_time = sensor_event_time.Seconds;
sts_o7_sensorData.event_sensor3_motion_duration = 0;
} else if (sts_rss_result == STS_RESULT_NO_MOTION)
{
sts_o7_sensorData.event_sensor3_motion_stop_time = sensor_event_time.Seconds;
sts_o7_sensorData.event_sensor3_start_timestamp = 0;
//sts_o7_sensorData.event_sensor3_motion_duration = 0;
}
last_sts_rss_time_stamp = sensor_event_time.Seconds;
}
/* motion sensor A: Motion/No-Motion Detection, Unconscious Detection */
void OnSensorRSS3AStateChanged(void)
{
SysTime_t sensor_event_time = SysTimeGetMcuTime();
#if 0
if ((sensor_event_time.Seconds - last_sts_rss_time_stamp) < 3 ) //less than 3 seconds ... return for flipping filter
{
return ;
}
#endif
if (sts_rss_result == STS_RESULT_MOTION)
{
sts_o7_sensorData.event_sensor3_motion_start_time = sensor_event_time.Seconds;
sts_o7_sensorData.event_sensor3_motion_duration = 0;
} else if (sts_rss_result == STS_RESULT_NO_MOTION)
{
sts_o7_sensorData.event_sensor3_motion_stop_time = sensor_event_time.Seconds;
sts_o7_sensorData.event_sensor3_start_timestamp = 0;
//sts_o7_sensorData.event_sensor3_motion_duration = 0;
}
last_sts_rss_time_stamp = sensor_event_time.Seconds;
}
/* motion sensor B, Fall Detection suggestionF */
void OnSensorRSS3BStateChanged(void)
{
SysTime_t sensor_event_time = SysTimeGetMcuTime();
uint32_t time_stamp=STS_Get_Date_Time_Stamp();
#if 0
if ((sensor_event_time.Seconds - last_sts_rss_time_stamp) < 3 ) //less than 3 seconds ... return for flipping filter
{
return ;
}
#endif
switch (sts_fall_rising_detected_result)
{
case STS_PRESENCE_NORMAL:
sts_o7_sensorData.event_sensor3_motion_stop_time = sensor_event_time.Seconds;
break;
case STS_PRESENCE_FALL:
//if (motion_in_hs_zone[0][motion_detected_count])
{
sts_o7_sensorData.event_sensor3_fall_start_time_stamp = time_stamp;
sts_o7_sensorData.event_sensor3_fall_start_time = sensor_event_time.Seconds;
//start counter of fall after rising up or other release actions/states
sts_o7_sensorData.event_sensor3_fall_duration = 0;
sts_o7_sensorData.event_sensor3_fall_stop_time_stamp = 0;
sts_o7_sensorData.event_sensor3_fall_stop_time = 0;
}
break;
case STS_PRESENCE_RISING:
sts_o7_sensorData.event_sensor3_fall_stop_time_stamp = time_stamp;
sts_o7_sensorData.event_sensor3_fall_stop_time = sensor_event_time.Seconds;
break;
case STS_PRESENCE_LAYDOWN:
break;
case STS_PRESENCE_STAYSTILL:
case STS_PRESENCE_NO_MOVEMENT:
case STS_PRESENCE_UNCONSCIOUS:
sts_o7_sensorData.event_sensor3_no_movement_start_time = sensor_event_time.Seconds;
sts_o7_sensorData.event_sensor3_unconcious_start_time = sensor_event_time.Seconds;
//sts_o7_sensorData.event_sensor3_unconcious_duration = 0;
//sts_o7_sensorData.event_sensor3_no_movement_duration = 0;
//sts_o7_sensorData.fall_laydown_duration = 0;
break;
default:
break;
}
last_sts_rss_time_stamp = sensor_event_time.Seconds;
}
/* motion sensor C: Over stay detection */
void OnSensorRSS3CStateChanged(void)
{
SysTime_t sensor_event_time = SysTimeGetMcuTime();
#if 0
if ((sensor_event_time.Seconds - last_sts_rss_time_stamp) < 3 ) //less than 3 seconds ... return for flipping filter
{
return ;
}
#endif
if ((sts_rss_result == STS_RESULT_MOTION)&&(last_sts_rss_result == STS_RESULT_NO_MOTION))
{
sts_o7_sensorData.event_sensor3_motion_start_time = sensor_event_time.Seconds;
sts_o7_sensorData.event_sensor3_motion_duration = 0;
} else if ((sts_rss_result == STS_RESULT_NO_MOTION)&&(last_sts_rss_result==STS_RESULT_MOTION))
{
sts_o7_sensorData.event_sensor3_motion_stop_time = sensor_event_time.Seconds;
//sts_o7_sensorData.event_sensor3_motion_duration = 0;
}
last_sts_rss_time_stamp = sensor_event_time.Seconds;
}
void OnSensor3StateChanged(void)
{
#if 0
SysTime_t sensor_event_time = SysTimeGetMcuTime();
// reserved... to be finalized 2024-06-03
if (sts_xxx_result)
sts_o7_sensorData.event_sensor4_start_time = sensor_event_time.Seconds;
else
sts_o7_sensorData.event_sensor4_stop_time = sensor_event_time.Seconds;
#endif
SysTime_t sensor_event_time = SysTimeGetMcuTime();
uint32_t time_stamp=STS_Get_Date_Time_Stamp();
if (sts_hall3_read==STS_Status_Alarm_Mute_Pushdown)
{
sts_o7_sensorData.event_sensor4_start_time = sensor_event_time.Seconds;
sts_o7_sensorData.event_sensor4_start_timestamp = time_stamp;
sts_o7_sensorData.event_sensor4_stop_time = 0;
sts_o7_sensorData.event_sensor4_duration = 0;
APP_LOG(TS_OFF, VLEVEL_L, "Alarm Mute PushDown ---Timer start: %u\r\n",sts_o7_sensorData.event_sensor4_start_time );
}else if (sts_hall3_read==STS_Status_Alarm_Mute_Release)
{
sts_o7_sensorData.event_sensor4_start_time = 0;
sts_o7_sensorData.event_sensor4_start_timestamp = 0;
sts_o7_sensorData.event_sensor4_stop_time = sensor_event_time.Seconds;
sts_o7_sensorData.event_sensor4_stop_timestamp = time_stamp;
//sts_o7_sensorData.over_stay_state = 0;
//sts_o7_sensorData.event_sensor2_duration = 0;
}
}
void OnSensor4StateChanged(void)
{
#if 0
SysTime_t sensor_event_time = SysTimeGetMcuTime();
// reserved... to be finalized 2024-06-03
if (sts_xxx_result)
sts_o7_sensorData.event_sensor4_start_time = sensor_event_time.Seconds;
else
sts_o7_sensorData.event_sensor4_stop_time = sensor_event_time.Seconds;
#endif
SysTime_t sensor_event_time = SysTimeGetMcuTime();
uint32_t time_stamp=STS_Get_Date_Time_Stamp();
if (sts_hall4_read==STS_Status_Alarm_Mute_Pushdown)
{
sts_o7_sensorData.event_sensor5_start_time = sensor_event_time.Seconds;
sts_o7_sensorData.event_sensor5_start_timestamp = time_stamp;
sts_o7_sensorData.event_sensor5_stop_time = 0;
sts_o7_sensorData.event_sensor5_duration = 0;
APP_LOG(TS_OFF, VLEVEL_L, "Alarm RESET PushDown ---Timer start: %u\r\n",sts_o7_sensorData.event_sensor5_start_time );
}else if (sts_hall4_read==STS_Status_Alarm_Mute_Release)
{
sts_o7_sensorData.event_sensor5_start_time = 0;
sts_o7_sensorData.event_sensor5_start_timestamp = 0;
sts_o7_sensorData.event_sensor5_stop_time = sensor_event_time.Seconds;
sts_o7_sensorData.event_sensor5_stop_timestamp = time_stamp;
//sts_o7_sensorData.over_stay_state = 0;
//sts_o7_sensorData.event_sensor2_duration = 0;
}
}
//卡尔曼滤波
float KalmanFilter(float inData)
{
static float prevData = 0; //先前数值
static float p = 10, q = 0.001, r = 0.001, kGain = 0; // q控制误差 r控制响应速度
p = p + q;
kGain = p / ( p + r ); //计算卡尔曼增益
inData = prevData + ( kGain * ( inData - prevData ) ); //计算本次滤波估计值
p = ( 1 - kGain ) * p; //更新测量方差
prevData = inData;
return inData; //返回滤波值
}
#if 0
uint8_t Radar_Data_Analysis(void)
{
uint8_t xReturn = 0;
const char* person = "Motion ";
const char* noperson = "No motion";
if(Radar_Data_Flag == 1)
{
if(strncmp((char *)USART3_RX_Buffer,person,strlen(person)) == 0){
xReturn = 1;
}
else if( strncmp((char *)USART3_RX_Buffer,noperson,strlen(noperson)) == 0){
xReturn = 0;
}
}
return xReturn;
}
void Radar_Filtering_clutter(volatile uint8_t *color)
{
_Bool pNew_Motion_Flag = 0;
static uint8_t Motion_Changed_Flag = 0;
static uint8_t numerator = 0;
static uint8_t denominator = 0;
pNew_Motion_Flag = Radar_Data_Analysis();
if(pNew_Motion_Flag != Motion_Flag){
Motion_Changed_Flag = 1;
}
if(Motion_Changed_Flag == 1)
{
denominator++;
if(pNew_Motion_Flag != Motion_Flag){
numerator++;
}
if(denominator >= Preset_denominator)
{
if(numerator >= Preset_numerator) //的确改变
{
Motion_Flag = !Motion_Flag;
if(Motion_Flag)
{
//M100C_Send_Data(10,0,ZhanYong);
*color = 2;
}
else
{
//M100C_Send_Data(10,0,KeYong);
*color = 1;
}
}
denominator = 0;
numerator = 0;
Motion_Changed_Flag = 0;
}
}
}
#endif
#if 0
#define PRESET_DENOMINATOR 5
#define PRESET_NUMERATOR (PRESET_DENOMINATOR - 3)
static uint8_t Motion_Changed_Flag = 0;
static uint8_t numerator = 0;
static uint8_t denominator = 0;
uint8_t STS_RSS_Filter(uint8_t pre_sts_rss_result)
{
_Bool pNew_Motion_Flag = 0;
uint8_t Motion_Flag = sts_rss_result, xReturn=0;
pNew_Motion_Flag = pre_sts_rss_result;
if(pNew_Motion_Flag != Motion_Flag){
Motion_Changed_Flag = 1;
}
denominator++;
if(Motion_Changed_Flag == 1)
{
if(pNew_Motion_Flag != Motion_Flag){
numerator++;
}
if(denominator >= PRESET_DENOMINATOR)
{
if(numerator >= PRESET_NUMERATOR) //SURE CHANGED
{
Motion_Flag = !Motion_Flag;
if(Motion_Flag)
{
//M100C_Send_Data(10,0,ZhanYong);
xReturn = 1;
}
else
{
//M100C_Send_Data(10,0,KeYong);
xReturn = 0;
}
}
denominator = 0;
numerator = 0;
Motion_Changed_Flag = 0;
}
}
return xReturn;
}
#endif
#define FILTER_LEN 20
#define SLIDING_WIN_LEN 10
static uint8_t motion_read[FILTER_LEN]={0};
static uint8_t idx_filter=0;
void STS_RSS_Filter_ring(void)
{
uint8_t sum_motion = 0;
for (uint8_t i=0; i<SLIDING_WIN_LEN; i++ )
{
Read_RingBuff(&motion_read[i]);
sum_motion += motion_read[i];
}
if (sum_motion >= (SLIDING_WIN_LEN-2))
{
sts_rss_result = STS_RESULT_MOTION;
} else {
sts_rss_result = STS_RESULT_NO_MOTION;
}
}
void STS_RSS_Filter(uint8_t pre_sts_rss_result)
{
_Bool pNew_Motion_Flag = 0;
static uint8_t Motion_Changed_Flag = 1;
static uint8_t numerator = PRESET_NUMERATOR;
static uint8_t denominator = PRESET_DENOMINATOR;
pNew_Motion_Flag = pre_sts_rss_result;
if(pNew_Motion_Flag != Motion_Flag)
{
Motion_Changed_Flag = 1;
}
if(Motion_Changed_Flag == 1)
{
denominator++;
if(pNew_Motion_Flag != Motion_Flag){
numerator++;
}
if(denominator >= PRESET_DENOMINATOR)
{
if(numerator >= PRESET_NUMERATOR) //的确改变
{
Motion_Flag = !Motion_Flag;
if(Motion_Flag)
{
//M100C_Send_Data(10,0,ZhanYong);
//*color = 2;
sts_rss_result = STS_RESULT_MOTION;
}
else
{
//M100C_Send_Data(10,0,KeYong);
//*color = 1;
sts_rss_result = STS_RESULT_NO_MOTION;
}
}
denominator = 0;
numerator = 0;
Motion_Changed_Flag = 0;
}
}
}
#if 0
#define FILTER_LEN 8
#define SLIDING_WIN_LEN 3
static uint8_t motion_read[FILTER_LEN]={0};
static uint8_t idx_filter=0;
uint8_t STS_RSS_Filter(uint8_t pre_sts_rss_result)
{
uint8_t j=0;
uint8_t sum_sliding_win=0;
motion_read[idx_filter] = pre_sts_rss_result;
switch(idx_filter)
{
case 1:
sum_sliding_win = motion_read[1] + motion_read[0] + motion_read[FILTER_LEN-1];
break;
case 2:
sum_sliding_win = motion_read[2] + motion_read[1] + motion_read[0];
break;
case 0:
sum_sliding_win = motion_read[0] + motion_read[FILTER_LEN-1] + motion_read[FILTER_LEN-2];
break;
default:
sum_sliding_win = motion_read[idx_filter] + motion_read[idx_filter-1] + motion_read[idx_filter-2];
break;
}
idx_filter = (idx_filter + 1) % FILTER_LEN;
uint8_t sum_filter = 0;
for (j=0; j<FILTER_LEN; j++)
{
sum_filter += motion_read[j];
}
return ((sum_sliding_win>=3))? 1:0;
}
#endif
RingBuff_t ringBuff;//创建一个ringBuff的缓冲区
/**
* @brief RingBuff_Init
* @param void
* @return void
* @note 初始化环形缓冲区
*/
void RingBuff_Init(void)
{
//初始化相关信息
ringBuff.Head = 0;
ringBuff.Tail = 0;
ringBuff.Lenght = 0;
}
/**
* @brief Write_RingBuff
* @param u8 data
* @return FLASE:环形缓冲区已满,写入失败;TRUE:写入成功
* @note 往环形缓冲区写入u8类型的数据
*/
uint8_t Write_RingBuff(uint8_t data)
{
if(ringBuff.Lenght >= RINGBUFF_LEN) //判断缓冲区是否已满
{
return FALSE;
}
ringBuff.Ring_Buff[ringBuff.Tail]=data;
// ringBuff.Tail++;
ringBuff.Tail = (ringBuff.Tail+1)%RINGBUFF_LEN;//防止越界非法访问
ringBuff.Lenght++;
return TRUE;
}
/**
* @brief Read_RingBuff
* @param u8 *rData用于保存读取的数据
* @return FLASE:环形缓冲区没有数据,读取失败;TRUE:读取成
* @note 从环形缓冲区读取一个u8类型的数据
*/
uint8_t Read_RingBuff(uint8_t *rData)
{
if(ringBuff.Lenght == 0)//判断非空
{
return FALSE;
}
*rData = ringBuff.Ring_Buff[ringBuff.Head];//先进先出FIFO从缓冲区头出
// ringBuff.Head++;
ringBuff.Head = (ringBuff.Head+1)%RINGBUFF_LEN;//防止越界非法访问
//ringBuff.Lenght--;
return TRUE;
}
/**
* @brief Read_RingBuff_Length
* @param void
* @return 环形缓冲区数据长度
* @note
*/
uint8_t Read_RingBuff_Length(void)
{
return ringBuff.Lenght;
}
/* USER CODE BEGIN EF */
/* USER CODE END EF */
/* Private Functions Definition -----------------------------------------------*/
/* USER CODE BEGIN PrFD */
/* USER CODE END PrFD */