#include "ble_action.h" #include "_string.h" #include "transcode.h" #include "debug.h" #include "tools.h" #include "user_config.h" #include "user_elect.h" #include "user_server.h" #include "user_led.h" #include "user_nfc.h" static void ble_action_set_rst(void); /* Flash data temporary storage */ __attribute__((aligned(8))) uint8_t block_buf[256]; /********************************************************************* * @fn Jump_OTA * * @brief Jump to OTA upgrade * * @return none */ void Jump_OTA(void) { uint16_t i; uint32_t ver_flag; /* Read the first block */ FLASH_read(OTA_DATAFLASH_ADDR, (uint8_t *)&block_buf[0], 4); FLASH_Unlock_Fast(); /* Erase the first block */ FLASH_ErasePage_Fast( OTA_DATAFLASH_ADDR ); /* Update Image information */ block_buf[0] = IMAGE_OTA_FLAG; block_buf[1] = IMAGE_FLAG_1; block_buf[2] = IMAGE_FLAG_2; block_buf[3] = IMAGE_FLAG_3; /* Programming DataFlash */ FLASH_ProgramPage_Fast(OTA_DATAFLASH_ADDR, (uint32_t *)&block_buf[0]); FLASH_Lock_Fast(); ble_action_set_rst(); } static upload_ble_data_func upload_ble_data = NULL; static ble_data_s last_test_data; static bool ble_connected = false; static uint32_t token = 0; static uint32_t unixTime_delay = 0; static uint32_t unixTime = 0; static void unixTime_pro(void) { if(unixTime_delay > 0) { unixTime_delay--; } else{ unixTime_delay = 1000 / BLE_ACTION_TICKS; unixTime++; } } uint32_t * get_unixTime(void) { return &(unixTime); } void set_unixTime(uint32_t value) { unixTime = value; } static void ble_owned_data_send(uint8_t *data, int len) { if(upload_ble_data != NULL) { upload_ble_data(data, len); } } static void ble_Return_Stat_Send(bool stat) { uint8_t data[4]={0}; if(stat == true) { data[0]='O'; data[1]='K'; data[2]=0; data[3]=0; } else{ data[0]='N'; data[1]='O'; data[2]='K'; data[3]=0; } ble_owned_data_send(data,4); } static void Set_Ble_Encrypt_Data(uint8_t *data,uint8_t len) { int pCipher_len = 0; PRINT("ble upload\n"); uint8_t *paradata = device_encrypt(MacAddr,(ble_connected == true)?token:0,data,len,&pCipher_len); ble_owned_data_send(paradata,pCipher_len); free(paradata); } static bool Set_ble_data_s_sendData(ble_data_s *ble_data) { uint8_t data[64]={0}; if(ble_data->len >= 55) { return false; } data[0] = ble_data->ins; data[1] = ble_data->data_type; data[2] = ble_data->len + 1; data[3] = ble_data->cmd; memcpy(&data[4], ble_data->data, ble_data->len); memcpy(&data[4 + ble_data->len], get_unixTime(), 4); memcpy(&data[8 + ble_data->len], &token, 4); #if AES_ENABLE == 1 Set_Ble_Encrypt_Data(data, ble_data->len + 12); #else ble_owned_data_send(data, ble_data->len + 12); #endif return true; } static void set_token(void) { token = Get_Rand(); token = get_gb_token(token); } void ble_connect_act(bool stat) { if(stat == false) { set_token(); ble_connected = false; vUser_led_set_alarm_view(LED_ALL_ALARM_BLE, false); // action_work.ble_conn_stat = false; // net_led_stat_pro(NET_LED_DISCONNECT); } else{ // upgrade_succ(); // net_led_stat_pro(NET_LED_CONNECT); } } static bool Get_Token_Act(ble_data_s *test_data) { if(test_data->len!=0x05 || test_data->data[0]!=0x00) { return false; } uint32_t unixtime = 0; memcpy(&unixtime, &(test_data->data[1]), 4); set_unixTime(unixtime); uint8_t data[16]={0}; data[0]=INS_TOKEN; data[1]=BLE_UPLOAD_SLAVE; data[2]=0x04; memcpy(&data[3],&token,4); memcpy(&data[7],get_unixTime(),4); memcpy(&data[11],&token,4); #if AES_ENABLE == 1 Set_Ble_Encrypt_Data(data,15); #else ble_owned_data_send(data, 15); #endif ble_connected = true; // action_work.ble_conn_stat = true; vUser_led_set_alarm_view(LED_ALL_ALARM_BLE, true); return true; } static bool Check_UnixTime_Token(uint8_t *data) { uint32_t master_token; uint32_t unixtime = 0; memcpy(&unixtime, data, 4); set_unixTime(unixtime); memcpy(&master_token, &data[4], 4); if(master_token!=token) { return false; } return true; } static void ble_devRst_set_stat_send(bool stat) { ble_data_s ble_data; ble_data.data_type = BLE_UPLOAD_SLAVE; ble_data.ins = INS_PARAM_SET; ble_data.len = 1; uint8_t data[1] = {0}; ble_data.cmd = PARAM_SET_RST; data[0] = (stat == true)?SET_PARAM_SUCCESS:SET_PARAM_FAILURE; ble_data.data = data; Set_ble_data_s_sendData(&ble_data); } static bool DevRst_Set_Act(uint8_t *data) { if(*data == 0xEE) { ble_devRst_set_stat_send(true); return true; } ble_devRst_set_stat_send(false); return false; } static void ble_devcan_baud_set_stat_send(bool stat) { ble_data_s ble_data; ble_data.data_type = BLE_UPLOAD_SLAVE; ble_data.ins = INS_PARAM_SET; ble_data.len = 1; uint8_t data[4] = {0}; ble_data.cmd = PARAM_SET_CAN; uint32_t baud = (uint32_t)user_config_param.can_baud; memcpy(data, &baud, 4); ble_data.data = data; Set_ble_data_s_sendData(&ble_data); } static bool Can_baud_Set_Act(ble_data_s *test_data) { uint32_t baud = 0; if(test_data->len == 5) { memcpy(&baud, &(test_data->data[1]), 4); if(true == user_config_save_can_baud(baud)) { return true; } } ble_devRst_set_stat_send(false); return false; } static bool Set_Param_Set_Act(ble_data_s *test_data) { bool stat = false; if(false == Check_UnixTime_Token(&test_data->data[test_data->len])) { return false; } switch(test_data->data[0]) { case PARAM_SET_CAN:stat = Can_baud_Set_Act(test_data);break; case PARAM_SET_RST: stat = DevRst_Set_Act(&(test_data->data[1]));break; //设备重启 default:return false; } return stat; } static void ble_get_canbaud_set_send(void) { ble_data_s ble_data; ble_data.data_type = BLE_UPLOAD_SLAVE; ble_data.ins = INS_PARAM_GET; ble_data.len = 5; uint8_t data[4] = {0}; ble_data.cmd = PARAM_GET_CAN; uint32_t baud = (uint32_t)user_config_param.can_baud; memcpy(data, &baud, 4); ble_data.data = data; Set_ble_data_s_sendData(&ble_data); } static bool Get_Param_Set_Act(ble_data_s *test_data) { if(false == Check_UnixTime_Token(&test_data->data[test_data->len])) { return false; } switch(test_data->data[0]) { case PARAM_GET_CAN: ble_get_canbaud_set_send();break; //CAN参数设置 default:return false; } return true; } void ble_get_nfc_send(ble_data_s *test_data) { ble_data_s ble_data; ble_data.data_type = BLE_UPLOAD_SLAVE; ble_data.ins = INS_DATA_GET; ble_data.len = 5; uint8_t data[5] = {0}; ble_data.cmd = DATA_GET_NFC; if(test_data->len != 2) { data[0] = 0xFF; } else{ uint8_t idx = test_data->data[1]; if(idx >= USER_NFC_MAX_COUNT) { data[0] = 0xFE; } else{ lock_data_s *lock = vUser_server_get_lock_data(); data[0] = (lock->lock_stat >> idx) & 0x01; memcpy(&data[1], lock->lock_id[idx], 4); } } ble_data.data = data; Set_ble_data_s_sendData(&ble_data); } static bool Get_Data_Act(ble_data_s *test_data) { if(false == Check_UnixTime_Token(&test_data->data[test_data->len])) { return false; } switch(test_data->data[0]) { case DATA_GET_NFC:ble_get_nfc_send(test_data);break; //获取挂锁NFC号 default:return false; } return true; } static bool Control_Data_Act(ble_data_s *test_data) { bool stat = false; if(false == Check_UnixTime_Token(&test_data->data[test_data->len])) { return false; } switch(test_data->data[0]) { case CONTROL_LOCK:break; //电磁锁控制 default:return false; } return stat; } static bool Get_Firmware_Act(uint8_t *test_data) { if(*test_data != 0x01) { return false; } ble_data_s ble_data; ble_data.data_type = BLE_UPLOAD_SLAVE; ble_data.ins = INS_FIRMWARE; ble_data.len = 2; uint8_t data[2] = {SOFTWARE_VERSION, HARDWARE_VERSION}; ble_data.cmd = FIRMWARE_GET; ble_data.data = data; Set_ble_data_s_sendData(&ble_data); return true; } static bool Rst_Firmware_Act(uint8_t *test_data) { if(*test_data == 0x01) { Jump_OTA(); } else{ return false; } ble_data_s ble_data; ble_data.data_type = BLE_UPLOAD_SLAVE; ble_data.ins = INS_FIRMWARE; ble_data.len = 1; uint8_t data[1] = {0}; ble_data.cmd = FIRMWARE_RST; data[0] = *test_data; ble_data.data = data; Set_ble_data_s_sendData(&ble_data); return true; } static bool Firmware_Data_Act(ble_data_s *test_data) { bool stat = false; if(false == Check_UnixTime_Token(&test_data->data[test_data->len])) { return false; } switch(test_data->data[0]) { case FIRMWARE_GET:stat = Get_Firmware_Act(&(test_data->data[1]));break; //获取固件版本号 case FIRMWARE_RST:stat = Rst_Firmware_Act(&(test_data->data[1]));break; //设备重启 default:return false; } return stat; } bool download_ble_data_callback(uint8_t *data, int len) { if(_strstr((char *)data,"rst=1")==0) { PRINT("SOFT RST!\n"); ble_action_set_rst(); ble_Return_Stat_Send(true); return true; } else if(_strstr((char *)data,"ENTER OTA")==0) { PRINT("ENTER OTA!\n"); Jump_OTA(); ble_Return_Stat_Send(true); return true; } else if(_strstr((char *)data,"configInit")==0) { PRINT("CONFIG INIT!\n"); set_user_config_param_init(&user_config_param); User_Config_Write_Config(); ble_Return_Stat_Send(true); return true; } else if(_strstr((char *)data, "open=") == 0) { int value = -1; if(1 == sscanf((char *)data, "open=%d", &value)) { if(value < ELECT_COUNT) { set_elect_work_stat(value, true); } } ble_Return_Stat_Send(true); return true; } else if(_strstr((char *)data, "close=") == 0) { int value = -1; if(1 == sscanf((char *)data, "close=%d", &value)) { if(value < ELECT_COUNT) { set_elect_work_stat(value, false); } } ble_Return_Stat_Send(true); return true; } #if AES_ENABLE == 1 uint8_t *paradata = device_decrypt(MacAddr, (ble_connected == true)?token:0, data, len); PRINT("Decrypt:\n"); print_hex(paradata, len); #else uint8_t *paradata = data; #endif ble_data_s test_data; test_data.ins = (ble_dev_ins_e)paradata[0]; test_data.data_type = (ble_dev_data_type_e)paradata[1]; if(test_data.data_type == BLE_UPLOAD_SLAVE) { #if AES_ENABLE == 1 free(paradata); #endif return false; } test_data.len = paradata[2]; test_data.data = ¶data[3]; bool stat = false; switch(test_data.ins) { case INS_TOKEN: stat = Get_Token_Act(&test_data);break; //获取token case INS_PARAM_SET: stat = Set_Param_Set_Act(&test_data);break; //参数设置指令 case INS_PARAM_GET: stat = Get_Param_Set_Act(&test_data);break; //获取设置参数指令 case INS_DATA_GET: stat = Get_Data_Act(&test_data);break; //获取数据指令 case INS_CONTROL: stat = Control_Data_Act(&test_data);break; //控制指令 case INS_FIRMWARE:stat = Firmware_Data_Act(&test_data);break; //固件获取指令 default:{ #if AES_ENABLE == 1 free(paradata); #endif }return false; } memcpy((uint8_t *)&last_test_data,(uint8_t *)&test_data,sizeof(ble_data_s)); #if AES_ENABLE == 1 free(paradata); #endif // if(stat == true) // { // net_led_stat_pro(NET_LED_DATA_OK); // Set_User_Work_Queue(USER_WORK_QUEUE_ONLINE); // } // else{ // net_led_stat_pro(NET_LED_DATA_NOK); // } return stat; } static void ble_action_set_rst(void) { vUser_led_set_alarm_view(LED_ALL_ALARM_RST, true); bStatus_t stat = tmos_start_reload_task(user_server_task_id, (1 << SERVER_BLE_RST), MS1_TO_SYSTEM_TIME(1000)); } /******************************************************************************* * @函数名称 vBle_action_init * @函数说明 初始化 * @输入参数 无 * @输出参数 无 * @返回参数 无 *******************************************************************************/ void vBle_action_init(void) { set_token(); } bool download_ble_file_callback(uint8_t *data, int len) { return download_ble_data_callback(data, len); } void set_upload_ble_data_func(upload_ble_data_func func) { upload_ble_data = func; }