在逗猫棒的基础上实现蓝牙转USB功能,目前功能已经实现,还需裁剪掉之前逗猫棒的业务程序
This commit is contained in:
@@ -0,0 +1,481 @@
|
||||
/****************************************************************************/
|
||||
/* bleproto.c
|
||||
*
|
||||
* Copyright (C) 2024 四川迈科创智科技有限公司
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************/
|
||||
/* Included Files */
|
||||
/****************************************************************************/
|
||||
|
||||
#include "bleproto.h"
|
||||
#include "ble_proto.h"
|
||||
|
||||
/****************************************************************************/
|
||||
/* Trace Definitions */
|
||||
/****************************************************************************/
|
||||
|
||||
/****************************************************************************/
|
||||
/* Pre-processor Definitions */
|
||||
/****************************************************************************/
|
||||
|
||||
/****************************************************************************/
|
||||
/* Private Types */
|
||||
/****************************************************************************/
|
||||
|
||||
/****************************************************************************/
|
||||
/* Private Function Prototypes */
|
||||
/****************************************************************************/
|
||||
|
||||
/****************************************************************************/
|
||||
/* Private Data */
|
||||
/****************************************************************************/
|
||||
|
||||
/****************************************************************************/
|
||||
/* Public Data */
|
||||
/****************************************************************************/
|
||||
|
||||
/****************************************************************************/
|
||||
/* Private Functions */
|
||||
/****************************************************************************/
|
||||
|
||||
/****************************************************************************/
|
||||
/* Public Functions */
|
||||
/****************************************************************************/
|
||||
|
||||
const char *libbleproto_version(void)
|
||||
{
|
||||
return BLEPROTO_API_VERSION;
|
||||
}
|
||||
|
||||
uint8_t bleproto_advdata_encode4bind(
|
||||
uint8_t data[31],
|
||||
int8_t txpower,
|
||||
uint8_t manucode[BLEPROTO_ADV_TLV_LENGTH_MANUCODE],
|
||||
uint8_t pcode[BLE_PROTO_ADV_LENGTH_PCODE],
|
||||
uint8_t prodcode[BLEPROTO_ADV_TLV_LENGTH_PRODCODE])
|
||||
{
|
||||
bleproto_adv_t adv = { 0 };
|
||||
/* adv1 */
|
||||
{
|
||||
adv.adv1.length = 0x02;
|
||||
adv.adv1.ad_type = BLEPROTO_ADV_TYPE_FLAGS;
|
||||
adv.adv1.ad_data = 0x06;
|
||||
}
|
||||
/* adv2 */
|
||||
// clang-format off
|
||||
{
|
||||
adv.adv2.length = 0x1B;
|
||||
adv.adv2.ad_type = BLEPROTO_ADV_TYPE_SVC_DATA_UUID16;
|
||||
|
||||
|
||||
adv.adv2.ad_data.service_data.uuid = BLEPROTO_ADV_SERVICE_UUID_TOBIND;
|
||||
/* spec_data */
|
||||
bleproto_adv_specdata_t *spec_data =
|
||||
&adv.adv2.ad_data.service_data.spec_data;
|
||||
|
||||
spec_data->version = BLEPORTO_ADV_SERVICE_SPEC_DATA_VER;
|
||||
spec_data->business = BELPROTO_ADV_SERVICE_SPEC_DATA_BUSINESS_NEARFIND;
|
||||
spec_data->rfu[0] = 0;
|
||||
spec_data->rfu[1] = 0;
|
||||
spec_data->txpower = txpower;
|
||||
|
||||
spec_data->manucode.type = BLEPROTO_ADV_TLV_TYPE_MANUCODE;
|
||||
spec_data->manucode.length = BLEPROTO_ADV_TLV_LENGTH_MANUCODE;
|
||||
memcpy(spec_data->manucode.value, manucode, BLEPROTO_ADV_TLV_LENGTH_MANUCODE);
|
||||
|
||||
spec_data->prodcode.type = BLEPROTO_ADV_TLV_TYPE_PRODCODE;
|
||||
spec_data->prodcode.length = BLEPROTO_ADV_TLV_LENGTH_PRODCODE;
|
||||
memcpy(spec_data->prodcode.value, prodcode, BLEPROTO_ADV_TLV_LENGTH_PRODCODE);
|
||||
|
||||
spec_data->separator = 0xFF;
|
||||
|
||||
memcpy(spec_data->selfdata, pcode, BLE_PROTO_ADV_LENGTH_PCODE);
|
||||
// spec_data->selfdata[0] = 0X30;
|
||||
// spec_data->selfdata[1] = 0X30;
|
||||
// spec_data->selfdata[2] = 0X30;
|
||||
// spec_data->selfdata[3] = 0X30;
|
||||
// spec_data->selfdata[4] = 0X30;
|
||||
// spec_data->selfdata[5] = 0X30;
|
||||
}
|
||||
// clang-format on
|
||||
|
||||
return bleproto_advdata_serialize(&adv, data, 31);
|
||||
}
|
||||
|
||||
void bleproto_advdata_encode4heartbeat(
|
||||
uint8_t data[31],
|
||||
int8_t txpower,
|
||||
uint8_t gwmac[6],
|
||||
uint8_t manucode[BLEPROTO_ADV_TLV_LENGTH_MANUCODE],
|
||||
uint8_t pcode[BLE_PROTO_ADV_LENGTH_PCODE],
|
||||
uint8_t prodcode[BLEPROTO_ADV_TLV_LENGTH_PRODCODE])
|
||||
{
|
||||
bleproto_adv_t adv = { 0 };
|
||||
/* adv1 */
|
||||
{
|
||||
adv.adv1.length = 0x02;
|
||||
adv.adv1.ad_type = BLEPROTO_ADV_TYPE_FLAGS;
|
||||
adv.adv1.ad_data = 0x06;
|
||||
}
|
||||
/* adv2 */
|
||||
// clang-format off
|
||||
{
|
||||
adv.adv2.length = 0x1B;
|
||||
adv.adv2.ad_type = BLEPROTO_ADV_TYPE_MFG_DATA;
|
||||
/* mfg_data */
|
||||
bleproto_advdata_mfg_t *mfg_data = &adv.adv2.ad_data.mfg_data;
|
||||
|
||||
memcpy(mfg_data->siot, pcode, BLE_PROTO_ADV_LENGTH_PCODE);
|
||||
#if 0
|
||||
mfg_data->siot[0] = 'S';
|
||||
mfg_data->siot[1] = 'I';
|
||||
mfg_data->siot[2] = 'O';
|
||||
mfg_data->siot[3] = 'T';
|
||||
mfg_data->siot[4] = '-';
|
||||
mfg_data->siot[5] = '1';
|
||||
#endif
|
||||
|
||||
/* HEARTBEAT */
|
||||
mfg_data->flag = BLEPROTO_ADV_FLAG_HEARTBEAT;
|
||||
|
||||
mfg_data->txpower = txpower;
|
||||
memcpy(mfg_data->gwmac, gwmac, 6);
|
||||
|
||||
mfg_data->manucode.type = BLEPROTO_ADV_TLV_TYPE_MANUCODE;
|
||||
mfg_data->manucode.length = BLEPROTO_ADV_TLV_LENGTH_MANUCODE;
|
||||
memcpy(mfg_data->manucode.value, manucode, BLEPROTO_ADV_TLV_LENGTH_MANUCODE);
|
||||
|
||||
mfg_data->prodcode.type = BLEPROTO_ADV_TLV_TYPE_PRODCODE;
|
||||
mfg_data->prodcode.length = BLEPROTO_ADV_TLV_LENGTH_PRODCODE;
|
||||
memcpy(mfg_data->prodcode.value, prodcode, BLEPROTO_ADV_TLV_LENGTH_PRODCODE);
|
||||
}
|
||||
// clang-format on
|
||||
|
||||
(void)bleproto_advdata_serialize(&adv, data, 31);
|
||||
}
|
||||
|
||||
uint8_t bleproto_advdata_encode4reconn(
|
||||
uint8_t data[31],
|
||||
int8_t txpower,
|
||||
uint8_t gwmac[6],
|
||||
uint8_t manucode[BLEPROTO_ADV_TLV_LENGTH_MANUCODE],
|
||||
uint8_t pcode[BLE_PROTO_ADV_LENGTH_PCODE],
|
||||
uint8_t prodcode[BLEPROTO_ADV_TLV_LENGTH_PRODCODE])
|
||||
{
|
||||
bleproto_adv_t adv = { 0 };
|
||||
/* adv1 */
|
||||
{
|
||||
adv.adv1.length = 0x02;
|
||||
adv.adv1.ad_type = BLEPROTO_ADV_TYPE_FLAGS;
|
||||
adv.adv1.ad_data = 0x06;
|
||||
}
|
||||
/* adv2 */
|
||||
// clang-format off
|
||||
{
|
||||
adv.adv2.length = 0x1B;
|
||||
adv.adv2.ad_type = BLEPROTO_ADV_TYPE_MFG_DATA;
|
||||
/* mfg_data */
|
||||
bleproto_advdata_mfg_t *mfg_data = &adv.adv2.ad_data.mfg_data;
|
||||
|
||||
memcpy(mfg_data->siot, pcode, BLE_PROTO_ADV_LENGTH_PCODE);
|
||||
#if 0
|
||||
mfg_data->siot[0] = 'S';
|
||||
mfg_data->siot[1] = 'I';
|
||||
mfg_data->siot[2] = 'O';
|
||||
mfg_data->siot[3] = 'T';
|
||||
mfg_data->siot[4] = '-';
|
||||
mfg_data->siot[5] = '1';
|
||||
#endif
|
||||
|
||||
/* RECONNECT */
|
||||
mfg_data->flag = BLEPROTO_ADV_FLAG_RECONNECT;
|
||||
|
||||
mfg_data->txpower = txpower;
|
||||
memcpy(mfg_data->gwmac, gwmac, 6);
|
||||
|
||||
mfg_data->manucode.type = BLEPROTO_ADV_TLV_TYPE_MANUCODE;
|
||||
mfg_data->manucode.length = BLEPROTO_ADV_TLV_LENGTH_MANUCODE;
|
||||
memcpy(mfg_data->manucode.value, manucode, BLEPROTO_ADV_TLV_LENGTH_MANUCODE);
|
||||
|
||||
mfg_data->prodcode.type = BLEPROTO_ADV_TLV_TYPE_PRODCODE;
|
||||
mfg_data->prodcode.length = BLEPROTO_ADV_TLV_LENGTH_PRODCODE;
|
||||
memcpy(mfg_data->prodcode.value, prodcode, BLEPROTO_ADV_TLV_LENGTH_PRODCODE);
|
||||
}
|
||||
// clang-format on
|
||||
|
||||
return bleproto_advdata_serialize(&adv, data, 31);
|
||||
}
|
||||
|
||||
int bleproto_advdata_decode(const uint8_t * data,
|
||||
uint8_t len,
|
||||
bleproto_adv_t *adv)
|
||||
{
|
||||
return bleproto_advdata_deserialize(data, len, adv);
|
||||
}
|
||||
|
||||
int bleproto_appdata_encode(uint8_t * txbuf,
|
||||
uint16_t size,
|
||||
uint8_t packetlen,
|
||||
bleproto_appdata_desc_t *desc)
|
||||
{
|
||||
int rc;
|
||||
uint16_t txbuf_size = size;
|
||||
|
||||
bleproto_appdata_t appdata;
|
||||
/* header */
|
||||
{
|
||||
appdata.header = desc->header;
|
||||
}
|
||||
/* data */
|
||||
if (appdata.header.msgtype == BLEPROTO_APPDATA_MSGTYPE_REQ) {
|
||||
switch (appdata.header.serviceid) {
|
||||
case E_BLEPROTO_SERVICE_ID_DEVICEINFO:
|
||||
rc = bleproto_encjson_deviceinfo_req(&desc->datast.deviceinfo_req,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_AUTHSETUP:
|
||||
rc = bleproto_encjson_authsetup_req(&desc->datast.authsetup_req,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_AUTHDELETE:
|
||||
rc = bleproto_encjson_authdelete_req(&desc->datast.authdelete_req,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_RUNCMD:
|
||||
rc = bleproto_encjson_runcmd_req(&desc->datast.runcmd_req,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_REPORTCMD:
|
||||
rc = bleproto_encjson_reportcmd_req(&desc->datast.reportcmd_req,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_DOACTION:
|
||||
rc = bleproto_encjson_doaction_req(&desc->datast.doaction_req,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_OTANOTIFY:
|
||||
rc = bleproto_encjson_otanotify_req(&desc->datast.otanotify_req,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_OTADATA:
|
||||
rc = bleproto_encjson_otadata_req(&desc->datast.otadata_req,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_REPORTCMD_V2:
|
||||
rc = ble_proto_pack(&desc->datast.runcmd_v2_req, appdata.data, sizeof(appdata.data));
|
||||
break;
|
||||
default:
|
||||
/* unkown serviceid */
|
||||
return (-1);
|
||||
}
|
||||
} else if (appdata.header.msgtype == BLEPROTO_APPDATA_MSGTYPE_RSP) {
|
||||
switch (appdata.header.serviceid) {
|
||||
case E_BLEPROTO_SERVICE_ID_DEVICEINFO:
|
||||
rc = bleproto_encjson_deviceinfo_rsp(&desc->datast.deviceinfo_rsp,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_AUTHSETUP:
|
||||
rc = bleproto_encjson_authsetup_rsp(&desc->datast.authsetup_rsp,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_AUTHDELETE:
|
||||
rc = bleproto_encjson_authdelete_rsp(&desc->datast.authdelete_rsp,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_RUNCMD:
|
||||
rc = bleproto_encjson_runcmd_rsp(&desc->datast.runcmd_rsp,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_REPORTCMD:
|
||||
rc = bleproto_encjson_reportcmd_rsp(&desc->datast.reportcmd_rsp,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_DOACTION:
|
||||
rc = bleproto_encjson_doaction_rsp(&desc->datast.doaction_rsp,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_OTANOTIFY:
|
||||
rc = bleproto_encjson_otanotify_rsp(&desc->datast.otanotify_rsp,
|
||||
appdata.data);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_OTADATA:
|
||||
rc = bleproto_encbin_otadata_rsp(&desc->datast.otadata_rsp,
|
||||
appdata.data);
|
||||
break;
|
||||
default:
|
||||
/* unkown serviceid */
|
||||
return (-1);
|
||||
}
|
||||
} else {
|
||||
/* unkown msgtype */
|
||||
return (-1);
|
||||
}
|
||||
/* failed to encjson struct */
|
||||
if (rc <= 0) {
|
||||
return (-1);
|
||||
}
|
||||
|
||||
/* datalen */
|
||||
appdata.header.datalen = (uint16_t)rc;
|
||||
|
||||
/* appdata_serialize */
|
||||
return bleproto_appdata_serialize(&appdata, packetlen, txbuf, txbuf_size);
|
||||
}
|
||||
|
||||
int bleproto_appdata_decode(uint8_t* rxbuf,
|
||||
uint16_t len,
|
||||
bleproto_appdata_desc_t *desc)
|
||||
{
|
||||
int rc, rlen;
|
||||
|
||||
bleproto_appdata_t appdata;
|
||||
|
||||
/* appdata_deserialize */
|
||||
rlen = bleproto_appdata_deserialize(rxbuf, len, &appdata);
|
||||
if (rlen <= 0) {
|
||||
return (rlen);
|
||||
}
|
||||
|
||||
/* header */
|
||||
{
|
||||
desc->header = appdata.header;
|
||||
}
|
||||
/* data */
|
||||
if (appdata.header.msgtype == BLEPROTO_APPDATA_MSGTYPE_REQ) {
|
||||
switch (appdata.header.serviceid) {
|
||||
case E_BLEPROTO_SERVICE_ID_DEVICEINFO:
|
||||
rc =
|
||||
bleproto_decjson_deviceinfo_req(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.deviceinfo_req);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_AUTHSETUP:
|
||||
rc = bleproto_decjson_authsetup_req(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.authsetup_req);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_AUTHDELETE:
|
||||
rc =
|
||||
bleproto_decjson_authdelete_req(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.authdelete_req);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_RUNCMD:
|
||||
rc = bleproto_decjson_runcmd_req(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.runcmd_req);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_REPORTCMD:
|
||||
rc = bleproto_decjson_reportcmd_req(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.reportcmd_req);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_DOACTION:
|
||||
rc = bleproto_decjson_doaction_req(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.doaction_req);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_OTANOTIFY:
|
||||
rc = bleproto_decjson_otanotify_req(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.otanotify_req);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_OTADATA:
|
||||
rc = bleproto_decjson_otadata_req(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.otadata_req);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_RUNCMD_V2:
|
||||
/* ble_proto_unpack 零拷贝指向 appdata.data;appdata 是栈变量,
|
||||
* 函数返回后指针会悬空。先拷到静态缓冲再 unpack,保证 desc 可用。 */
|
||||
{
|
||||
static uint8_t s_runcmd_v2_raw[BLEPROTO_APPDATA_DATA_MAX_SZ];
|
||||
uint16_t raw_len = appdata.header.datalen;
|
||||
if (raw_len > sizeof(s_runcmd_v2_raw)) {
|
||||
return (-1);
|
||||
}
|
||||
memcpy(s_runcmd_v2_raw, appdata.data, raw_len);
|
||||
printf("runcmd_v2_req");
|
||||
rc = ble_proto_unpack(s_runcmd_v2_raw, raw_len, &desc->datast.runcmd_v2_req);
|
||||
printf("runcmd_v2_req rc = %d", rc);
|
||||
}
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_REPORTCMD_V2:
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_OTADATA_V2:
|
||||
break;
|
||||
default:
|
||||
/* unkown serviceid */
|
||||
return (-1);
|
||||
}
|
||||
} else if (appdata.header.msgtype == BLEPROTO_APPDATA_MSGTYPE_RSP) {
|
||||
switch (appdata.header.serviceid) {
|
||||
case E_BLEPROTO_SERVICE_ID_DEVICEINFO:
|
||||
rc =
|
||||
bleproto_decjson_deviceinfo_rsp(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.deviceinfo_rsp);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_AUTHSETUP:
|
||||
rc = bleproto_decjson_authsetup_rsp(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.authsetup_rsp);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_AUTHDELETE:
|
||||
rc =
|
||||
bleproto_decjson_authdelete_rsp(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.authdelete_rsp);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_RUNCMD:
|
||||
rc = bleproto_decjson_runcmd_rsp(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.runcmd_rsp);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_REPORTCMD:
|
||||
rc = bleproto_decjson_reportcmd_rsp(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.reportcmd_rsp);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_DOACTION:
|
||||
rc = bleproto_decjson_doaction_rsp(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.doaction_rsp);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_OTANOTIFY:
|
||||
rc = bleproto_decjson_otanotify_rsp(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.otanotify_rsp);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_OTADATA:
|
||||
rc = bleproto_debin_otadata_rsp(appdata.data,
|
||||
appdata.header.datalen,
|
||||
&desc->datast.otadata_rsp);
|
||||
break;
|
||||
case E_BLEPROTO_SERVICE_ID_REPORTCMD_V2:
|
||||
printf("reportcmd_v2_rsp");
|
||||
rc = ble_proto_unpack(appdata.data, appdata.header.datalen, &desc->datast.reportcmd_v2_rsp);
|
||||
printf("reportcmd_v2_rsp rc = %d", rc);
|
||||
break;
|
||||
default:
|
||||
/* unkown serviceid */
|
||||
return (-1);
|
||||
}
|
||||
} else {
|
||||
/* unkown msgtype */
|
||||
return (-1);
|
||||
}
|
||||
/* failed to decjson struct */
|
||||
if (rc < 0) {
|
||||
return (-1);
|
||||
}
|
||||
|
||||
return (rlen);
|
||||
}
|
||||
/****************************************************************************/
|
||||
/* */
|
||||
/* End of file. */
|
||||
/* */
|
||||
/****************************************************************************/
|
||||
Reference in New Issue
Block a user