mcu_hi3321_watch/tjd/ble/protocol/ble_management_server.c
2025-05-26 20:15:20 +08:00

416 lines
13 KiB
C

/******************************************************************************
@brief 实现APP与设备握手连接
******************************************************************************/
#include "am_util_debug.h"
#include "sys_config.h"
#include "FreeRTOS.h"
#include "task.h"
#include "ble_management_server.h"
#include "user_adapter.h"
#include "amotas_api.h"
#include "task_ble.h"
#include "ble_data_transmission.h"
#include "sys_typedef.h"
#include "ui_port_resource.h"
#include "task_ui.h"
//#include "fs_user_app.h"
//#include "data_log.h"
#include "rtc_api.h"
#include "ui_ble_pair.h"
#include "ui_port_fw.h"
#include "fs_api.h"
#include "fs_user_init.h"
#include "sql_setting.h"
static conn_param_t conn_param=
{
FRAM_MAX_SIZ, //链路层最大帧长度
BLE_NOTIF_LEN, //MTU大小
0x03,//500, // 最大超时时间 3s
};
static bond_info_t user_bond_info = {0}; //用户绑定信息
static uint8_t user_iphone_id[6] = {0};
//*****************************************************************************
//
// brief: 输出反向的mac地址数组
// example: 如果 mac_addr = {06,05,04,03,02,01};
// 输出"{01,02,03,04,05,06}"
//*****************************************************************************
extern uint8_t* HciVscGetCustom_BDAddr(void);
//void user_get_reverse_ble_mac(uint8_t *output, uint16_t len)
//{
// uint8_t* pMacAddr = NULL;
// uint8_t i = 0;
// if(output == NULL || len < 6)
// return;
// pMacAddr = HciVscGetCustom_BDAddr();
// for(; i < 6; i++) {
// output[i] = pMacAddr[5 - i];
// }
//}
uint8_t GetBandStatus(void)
{
return user_bond_info.status;
}
void SetBandstatus(uint8_t status)
{
user_bond_info.status = status;
}
// 获取绑定手机的操作系统 //0:Android; 1:ios
uint8_t GetBandPhoneOS(void)
{
return user_bond_info.os;
}
// 设备是否绑定过
bool IsTheDeviceBuand(void)
{
uint8_t bondIdEmpty[BDA_ADDR_LEN] = {0};
uint8_t bondIdFull[BDA_ADDR_LEN] = {0xff};
if((memcmp(user_bond_info.id, bondIdEmpty, BDA_ADDR_LEN) == 0) || (memcmp(user_bond_info.id, bondIdFull, BDA_ADDR_LEN) == 0))
{
return false;
}
else
{
return true;
}
}
void LoadBleConfig(void)
{
int len = 0;
char path[48];
bool is_dir;
fs_user_get_dir_by_full_path(FILE_CONFIG_BLUETOOTH, path);
if(fs_api_dir_exist(path) != RET_SUCCESS) {
fs_user_create_dir(path);
}
if(fs_api_stat(FILE_CONFIG_BLUETOOTH,&is_dir) != sizeof(user_bond_info)) {
//文件长度不符
ble_printf("notify message file length err,need default\r\n");
goto NEED_DEFAULT;
}
len = fs_api_file_load(FILE_CONFIG_BLUETOOTH, 0, &user_bond_info, sizeof(user_bond_info));
if(len != sizeof(user_bond_info)) {
//读取文件的长度不符
ble_printf("read notify message file err,ret=%d,need default\r\n", len);
goto NEED_DEFAULT;
}
return;
NEED_DEFAULT:
memset(&user_bond_info, 0, sizeof(user_bond_info));
SaveBleConfig();
}
void SaveBleConfig(void)
{
fs_api_file_store(FILE_CONFIG_BLUETOOTH, 0, &user_bond_info, sizeof(user_bond_info));
}
// 在没有文件路径的情况下保存文件,连接复位测试用
void SavePairingFileWithoutDir(void)
{
#if 1
char path[48];
fs_user_get_dir_by_full_path(FILE_CONFIG_BLUETOOTH, path);
if(fs_api_dir_exist(path) != RET_SUCCESS) {
fs_user_create_dir(path);
}
SaveBleConfig();
#endif
}
void BleConifgInit(void)
{
LoadBleConfig();
}
void BleBondReqRespond(uint8_t BondStatus)
{
uint16_t write_idx = 0;
uint8_t buf_temp[5] = {0};
if(BondStatus == BAND_REJECT) // 协议回复的绑定拒绝与设备定义的不一致
BondStatus = PROTOCOL_BAND_REJECT;
buf_temp[write_idx++] = 0x03; //LTV - length
buf_temp[write_idx++] = get_bt_bond_status_type; //type
buf_temp[write_idx++] = BondStatus; //value
BLE_SendFrameById(DEVICE_MANAGEMENT_SERVER, BLE_BOND_REQ_ID, buf_temp, write_idx);
}
void UserPairOperate(uint8_t pair_opcode)
{
int ret;
uint8_t *p_save_data;
uint32_t len;
char* path;
BleBondReqRespond(pair_opcode);
if((pair_opcode == AGREE_PAIR_RESPONSE) || (pair_opcode == FORCE_AGREE_PAIR))
{
ble_printf("Device Pairing Success.\r\n");
user_bond_info.status = BAND_SUCC;
memcpy(user_bond_info.id, user_iphone_id, sizeof(user_iphone_id));
//log_api_record_action(rtc_api_get_utc_timestamp(), EVT_BLE_MANAGE, INFO1_BLE_PAIRING, pair_opcode, 0, NULL);
sql_setting_set_ble_bind(true);
SaveBleConfig();
p_save_data = sql_setting_get_info(&len,&path);
ret = fs_api_file_store(path, 0, p_save_data, len);
ble_printf("[%s] ret=%d len=%d\r\n",path,ret,len);
}
else
{
ble_printf("Device Pairing fail.\r\n");
if(pair_opcode == REJECT_PAIR_RESPONSE)
{
user_bond_info.status = BAND_REJECT;
}
else if(pair_opcode == TIMEOUT_AUTO_REJECT_PAIR_RESPONSE)
{
user_bond_info.status = BAND_TIMEOUT;
}
vTaskDelay(1000);
amota_disconnect();
}
}
/*****************************************************************************
功能描述 : 4.1.1连接参数协商
*****************************************************************************/
void user_rev_conn_param_cmd(uint8_t *in_data,uint16_t in_len,uint8_t
*out_data,uint16_t *out_len)
{
uint16_t write_idx = 0;
protocol_data_info_t data_info = {0};
uint8_t rev_ipone_type_flag = 0;
do
{
user_get_data_info(&data_info,&in_data,&in_len);
switch((data_info.type &0x7F))
{
case max_frame_size_type:
out_data[write_idx++]=4;
out_data[write_idx++]=data_info.type;
out_data[write_idx++]=((conn_param.max_frame_size >> 8) & 0xff);
out_data[write_idx++]=((conn_param.max_frame_size) & 0xff);
break;
case max_transimission_unit_type:
out_data[write_idx++]=4;
out_data[write_idx++]=data_info.type;
conn_param.max_trans_unit = user_app_mtu_get();
out_data[write_idx++] = ((conn_param.max_trans_unit >> 8) & 0xff);;
out_data[write_idx++] = ((conn_param.max_trans_unit ) & 0xff);
break;
case max_transimission_timeout_type:
out_data[write_idx++]=4;
out_data[write_idx++]=data_info.type;
out_data[write_idx++]=((conn_param.max_trans_timeout>> 8) & 0xff);
out_data[write_idx++]=((conn_param.max_trans_timeout) & 0xff);
ble_printf("upload mtu is %d\n", conn_param.max_trans_unit);
break;
case phone_operating_system_type:
rev_ipone_type_flag = 1;
user_bond_info.os = *in_data;
ble_printf("****** phone_operating_system_type: os = %d *****\r\n", user_bond_info.os);
break;
default:
break;
}
in_data= data_info.p_data;
in_data+=(data_info.len);
in_len-=(2+data_info.len);
if(in_len>FRAM_MAX_SIZ)
{
in_len=0;
}
}
while(in_len);
if(rev_ipone_type_flag == 0)
{// 若app未发手机类型则默认为安卓类型
user_bond_info.os = ANDROID_PHONE;
}
*out_len=write_idx;
}
/*****************************************************************************
功能描述 : 4.1.2 查询蓝牙绑定状态
*****************************************************************************/
void user_rev_get_ble_bond_status(uint8_t *in_data, uint16_t in_len, uint8_t
*out_data, uint16_t *out_len)
{
// uint8_t i;
uint16_t write_idx = 0, bond_status_index = 0;
protocol_data_info_t data_info = {0};
ble_printf("user_rev_get_ble_bond_status\n");
memset(user_bond_info.phone_mac_addr, 0xff, sizeof(user_bond_info.phone_mac_addr));
do {
user_get_data_info(&data_info, &in_data, &in_len);
switch((data_info.type & 0x7F)) {
case get_bt_bond_status_type:
out_data[write_idx++] = 3;
out_data[write_idx++] = get_bt_bond_status_type;
bond_status_index = write_idx;
out_data[write_idx++] = user_bond_info.status;
break;
case get_bt_bond_id_type:
if(data_info.len == 6) {
// 比较ID是否与上次连接的手机ID一致
// for(i = 0; i < data_info.len; i++) {
// ble_printf("get_bound_status memcmp id[%d]= 0x%x,in_data[%d]=0x%x.\r\n", i, user_bond_info.id[i], i, in_data[i]);
// }
if(memcmp(user_bond_info.id, in_data, data_info.len) == 0 && sql_setting_get_ble_bind()) {
user_bond_info.status = BAND_SUCC;
ble_printf(" connect succ!!! \r\n");
} else {
user_bond_info.status = NOT_BAND; // 手环与手机未绑定
ble_printf("NOT_BAND!!! \r\n");
}
out_data[bond_status_index] = user_bond_info.status;
}
break;
case get_bt_device_mac_addr_type:
out_data[write_idx++] = 8; //手环蓝牙地址需要带:
out_data[write_idx++] = get_bt_device_mac_addr_type;
user_get_reverse_ble_mac(user_bond_info.device_mac_addr, 6);
memcpy(&out_data[write_idx], user_bond_info.device_mac_addr, 6);
write_idx += 6;
break;
default:
break;
}
in_data = data_info.p_data;
in_data += (data_info.len);
in_len -= (2 + data_info.len);
if(in_len > FRAM_MAX_SIZ) {
in_len = 0;
}
} while(in_len);
if(data_info.error) {
write_idx = user_set_protocol_error(out_data, DEVICE_MANAGEMENT_SERVER, data_info.error);
}
*out_len = write_idx;
}
/*****************************************************************************
功能描述 : 4.1.3 蓝牙绑定请求
*****************************************************************************/
void user_rev_req_bond(uint8_t *in_data, uint16_t in_len, uint8_t
*out_data, uint16_t *out_len)
{
uint16_t write_idx = 0;
uint16_t bond_bit = 0;
protocol_data_info_t data_info = {0};
// log_api_record_action(rtc_api_get_utc_timestamp(), EVT_BLE_MANAGE, INFO1_BLE_PAIRING, INFO2_BLE_PAIRING_REQ, 0, NULL);
do {
user_get_data_info(&data_info, &in_data, &in_len);
switch((data_info.type & 0x7F)) {
case require_bt_bond_type:
bond_bit = bond_bit | (1 << require_bt_bond_type);
break;
case bt_bond_os_type:
bond_bit = bond_bit | (1 << bt_bond_os_type);
user_bond_info.os = *in_data;
ble_printf("user_bond_info.os = %d\r\n",user_bond_info.os);
break;
case bt_bond_id_type:
if(data_info.len == 6) {
bond_bit = bond_bit | (1 << bt_bond_id_type);
memcpy(user_iphone_id, in_data, data_info.len);
}
break;
case bt_bond_key_type:
if(data_info.len == 16) {
bond_bit = bond_bit | (1 << bt_bond_key_type);
memcpy(user_bond_info.key, in_data, data_info.len);
}
break;
case bt_bond_IV_type:
if(data_info.len == 16) {
bond_bit = bond_bit | (1 << bt_bond_IV_type);
memcpy(user_bond_info.iv, in_data, data_info.len);
}
break;
default:
break;
}
in_data = data_info.p_data;
in_data += (data_info.len);
in_len -= (2 + data_info.len);
if(in_len > FRAM_MAX_SIZ) {
in_len = 0;
}
} while(in_len);
DeviceReadPeerMacAddr(user_bond_info.phone_mac_addr);
if(data_info.error) {
write_idx = user_set_protocol_error(out_data, DEVICE_MANAGEMENT_SERVER, data_info.error);
} else {
ble_printf("user_bond_info.status is %d\n", user_bond_info.status);
user_bond_info.status = BAND_REQUEST;
if(ui_get_resource_check_result()) {
ui_port_send_sys_remind_event(EVENT_REMIND_PAIR,PAIR_REQUEST_STATE,NULL,0);
} else {
ble_printf("force pair because resource is bad\r\n");
task_ble_notify(BLE_PAIRING_OPER_MSG, BAND_SUCC);
}
}
*out_len = write_idx;
}
const p_func_t user_manamagement_server_func[mamagement_server_max_ID]=
{
user_null_func,
user_rev_conn_param_cmd, //4.1.1
user_rev_get_ble_bond_status, //4.1.2
user_rev_req_bond, //4.1.3
};