BLE协议栈之Central事件慢慢谈
来源:互联网 发布:mac电脑照片怎么删除 编辑:程序博客网 时间:2024/05/21 11:07
BLE协议栈Central 工程中与广播连接建立的事件
最近在改写BLE协议栈,需要实现实时发现周边从设备,并建立连接,获取RSSI的功能,没什么难度,但着实将各个事件好好看了一遍。曾经看到一位大神说相同的任务使用事件触发方式,不同的任务使用消息传递方式。冥冥之中突然来了感觉~
BLE进行广播和建立连接的事件主要实现是在simpleBLECentralEventCB的回调函数中:
所有使用到的变量都在联合体gapCentralRoleEvent_t中:
typedef union{ gapEventHdr_t gap; //!< GAP_MSG_EVENT and status. gapDeviceInitDoneEvent_t initDone; //!< GAP initialization done. 本机信息 gapDeviceInfoEvent_t deviceInfo;//!< Discovery device information event structure. 从机信息 gapDevDiscEvent_t discCmpl;//!< Discovery complete event structure.从机信息(全部) gapEstLinkReqEvent_t linkCmpl; //!< Link complete event structure. gapLinkUpdateEvent_t linkUpdate; //!< Link update event structure. gapTerminateLinkEvent_t linkTerminate; //!< Link terminated event structure.} gapCentralRoleEvent_t; // central.h
1 板级初始化事件:GAP_DEVICE_INIT_DONE_EVENT
case GAP_DEVICE_INIT_DONE_EVENT: // 初始化 // 是本机GAP层的初始化信息 在运行到GAPCentralRole_StartDevice函数被回调{ LCD_WRITE_STRING( bdAddr2Str( pEvent->initDone.devAddr ), HAL_LCD_LINE_2 );}break;
详解:
作用:进行GAP层的初始化详解:/** * GAP_DEVICE_INIT_DONE_EVENT message format. This message is sent to the * app when the Device Initialization is done [initiated by calling * GAP_DeviceInit()]. gap.h */typedef struct{ osal_event_hdr_t hdr; //!< GAP_MSG_EVENT and status uint8 opcode; //!< GAP_DEVICE_INIT_DONE_EVENT uint8 devAddr[B_ADDR_LEN]; //!< Device's BD_ADDR 本机的MAC地址 uint16 dataPktLen; //!< HC_LE_Data_Packet_Length 初始化长度为27 uint8 numDataPkts; //!< HC_Total_Num_LE_Data_Packets 初始化为4} gapDeviceInitDoneEvent_t;
2 搜索从机事件(每搜到一个从机进入一次):GAP_DEVICE_INFO_EVENT
case GAP_DEVICE_INFO_EVENT: //过程量 从机的广播数据 搜索到之后添加到从机列表中 { char temprssiarg[4]={0}; // if filtering device discovery results based on service UUID if ( DEFAULT_DEV_DISC_BY_SVC_UUID == TRUE ) { if ( simpleBLEFindSvcUuid( SIMPLEPROFILE_SERV_UUID, pEvent->deviceInfo.pEvtData, pEvent->deviceInfo.dataLen ) ) { simpleBLEAddDeviceInfo( pEvent->deviceInfo.addr, pEvent->deviceInfo.addrType ); } } }
作用: 每搜索到一个从设备时,都会进入该事件,并使用simpleBLEAddDeviceInfo加入到扫描结果列表中,deviceInfo.addr中储存着当前正被扫描到从设备地址,扫描从机的数量(simpleBLEScanRes)在simpleBLEAddDeviceInfo中增加!
详解:
** * GAP_DEVICE_INFO_EVENT message format. This message is sent to the * app during a Device Discovery Request, when a new advertisement or scan * response is received. //gap.h */typedef struct{ osal_event_hdr_t hdr; //!< GAP_MSG_EVENT and status uint8 opcode; //!< GAP_DEVICE_INFO_EVENT uint8 eventType; //!< Advertisement Type: @ref GAP_ADVERTISEMENT_TYPE_DEFINES uint8 addrType; //!< address type: @ref GAP_ADDR_TYPE_DEFINES uint8 addr[B_ADDR_LEN]; //!< Address of the advertisement or SCAN_RSP 从机MAC地址 int8 rssi; //!< Advertisement or SCAN_RSP RSSI 从机RSSI值 uint8 dataLen; //!< Length (in bytes) of the data field (evtData) uint8 *pEvtData; //!< Data field of advertisement or SCAN_RSP} gapDeviceInfoEvent_t;
3 搜索从机事件(搜索完毕时进入一次):GAP_DEVICE_DISCOVERY_EVENT
case GAP_DEVICE_DISCOVERY_EVENT: //结果量 // 搜索周边广播从机事件 显示搜索结果 { // discovery complete simpleBLEScanning = FALSE; // if not filtering device discovery results based on service UUID if ( DEFAULT_DEV_DISC_BY_SVC_UUID == FALSE ) { // Copy results simpleBLEScanRes = pEvent->discCmpl.numDevs; osal_memcpy( simpleBLEDevList, pEvent->discCmpl.pDevList, (sizeof( gapDevRec_t ) * pEvent->discCmpl.numDevs) ); } char temp_simpleBLEScanRes[10]="Find : \n"; FineDeviceNum=FindDeviceNum=simpleBLEScanRes;//***************************************************************** 扫描的数量 temp_simpleBLEScanRes[8] = simpleBLEScanRes+'0'; Uart0Send_String(temp_simpleBLEScanRes,10);//*********************************** /******************************************************************************************************/ // initialize scan index to last device simpleBLEScanIdx = simpleBLEScanRes; IsPeriodicStart=1; } break;
作用:程序运行到这一步可以知道当前有多少个已经被扫描到的从设备,且它们的地址被保存到simpleBLEDevList里。
搜索结果列表 // Scan result list
static gapDevRec_t simpleBLEDevList[DEFAULT_MAX_SCAN_RES]; // 扫描结果列表
详解:
/** * Type of device discovery (Scan) to perform. */typedef struct{ uint8 eventType; //!< Indicates advertising event type used by the advertiser: @ref GAP_ADVERTISEMENT_TYPE_DEFINES uint8 addrType; //!< Address Type: @ref GAP_ADDR_TYPE_DEFINES uint8 addr[B_ADDR_LEN]; //!< Device's Address // 储存着当前搜索到的设备地址 最大可见扫描数量8} gapDevRec_t; 搜索结果结构体/** * GAP_DEVICE_DISCOVERY_EVENT message format. This message is sent to the * Application after a scan is performed. */typedef struct{ osal_event_hdr_t hdr; //!< GAP_MSG_EVENT and status uint8 opcode; //!< GAP_DEVICE_DISCOVERY_EVENT uint8 numDevs; //!< Number of devices found during scan gapDevRec_t *pDevList; //!< array of device records} gapDevDiscEvent_t; 搜索结果事件结构体
Note: 需要知道一个从设备的RSSI值,只需知道从设备的MAC地址信息在simpleBLEDevList中即可!
4 连接建立事件:GAP_LINK_ESTABLISHED_EVENT
本事件里开起一个定时器,事件连接超时断开!
case GAP_LINK_ESTABLISHED_EVENT: { if ( pEvent->gap.hdr.status == SUCCESS ) { simpleBLEState = BLE_STATE_CONNECTED; simpleBLEConnHandle = pEvent->linkCmpl.connectionHandle; simpleBLEProcedureInProgress = TRUE; // If service discovery not performed initiate service discovery if ( simpleBLECharHdl == 0 ) { osal_start_timerEx( simpleBLETaskId, START_DISCOVERY_EVT, DEFAULT_SVC_DISCOVERY_DELAY ); } // SerialPrintString("Connected: "); // Uart0Send_String( bdAddr2Str( pEvent->linkCmpl.devAddr ), sizeof(bdAddr2Str( pEvent->linkCmpl.devAddr ))); // for(int i=0;i<10000;i++); for(int i=0;i<10000;i++); LCD_WRITE_STRING( bdAddr2Str( pEvent->linkCmpl.devAddr ), HAL_LCD_LINE_2 ); for(int i=0;i<10000;i++); // Uart0Send_String("12222",5); //LCD_WRITE_STRING( "Connected", HAL_LCD_LINE_1 ); /*********** 2015年1月8日 不间断的搜寻周围的从设备 ************** 建立连接后读取当前的RSSI 值***********************************************************************************************/ if ( simpleBLEState == BLE_STATE_CONNECTED ) { if ( !simpleBLERssi ) { simpleBLERssi = TRUE; GAPCentralRole_StartRssi( simpleBLEConnHandle, DEFAULT_RSSI_PERIOD ); } else { simpleBLERssi = FALSE; GAPCentralRole_CancelRssi( simpleBLEConnHandle ); LCD_WRITE_STRING( "RSSI Cancelled", HAL_LCD_LINE_1 ); // SerialPrintString("RSSI Cancelled\r\n"); } } /****************************************************************************************************************/ } else { simpleBLEState = BLE_STATE_IDLE; simpleBLEConnHandle = GAP_CONNHANDLE_INIT; simpleBLERssi = FALSE; simpleBLEDiscState = BLE_DISC_STATE_IDLE; LCD_WRITE_STRING( "Connect Failed", HAL_LCD_LINE_1 ); // SerialPrintString("Connect Failed: "); LCD_WRITE_STRING_VALUE( "Reason:", pEvent->gap.hdr.status, 10, HAL_LCD_LINE_2 ); GAPCentralRole_CancelRssi( simpleBLEConnHandle ); /*********** 2015年1月8日 不间断的搜寻周围的从设备 ************** 连接错误 主机从新进行搜索***********************************************************************************************/ simpleBLEScanning = TRUE; simpleBLEScanRes = 0; LCD_WRITE_STRING( "Discovering...", HAL_LCD_LINE_1 ); LCD_WRITE_STRING( "", HAL_LCD_LINE_2 ); GAPCentralRole_StartDiscovery( DEFAULT_DISCOVERY_MODE, DEFAULT_DISCOVERY_ACTIVE_SCAN, DEFAULT_DISCOVERY_WHITE_LIST ); /*****************************************************************************************************/ // SerialPrintValue("Reason:", pEvent->gap.hdr.status,10); } } break;
详解:/** * GAP_LINK_ESTABLISHED_EVENT message format. This message is sent to the app * when the link request is complete.<BR> * <BR> * For an Observer, this message is sent to complete the Establish Link Request.<BR> * For a Peripheral, this message is sent to indicate that a link has been created. */typedef struct{ osal_event_hdr_t hdr; //!< GAP_MSG_EVENT and status uint8 opcode; //!< GAP_LINK_ESTABLISHED_EVENT uint8 devAddrType; //!< Device address type: @ref GAP_ADDR_TYPE_DEFINES uint8 devAddr[B_ADDR_LEN]; //!< Device address of link uint16 connectionHandle; //!< Connection Handle from controller used to ref the device uint16 connInterval; //!< Connection Interval uint16 connLatency; //!< Conenction Latency uint16 connTimeout; //!< Connection Timeout uint8 clockAccuracy; //!< Clock Accuracy} gapEstLinkReqEvent_t;
5 连接超时事件 : GAP_LINK_TERMINATED_EVENT
case GAP_LINK_TERMINATED_EVENT: { simpleBLEState = BLE_STATE_IDLE; simpleBLEConnHandle = GAP_CONNHANDLE_INIT; simpleBLERssi = FALSE; simpleBLEDiscState = BLE_DISC_STATE_IDLE; simpleBLECharHdl = 0; simpleBLEProcedureInProgress = FALSE; LCD_WRITE_STRING( "Disconnected", HAL_LCD_LINE_1 ); // SerialPrintString("Disconnected: "); LCD_WRITE_STRING_VALUE( "Reason:", pEvent->linkTerminate.reason, 10, HAL_LCD_LINE_2 ); // SerialPrintValue("Reason:", pEvent->linkTerminate.reason,10); }
- BLE协议栈之Central事件慢慢谈
- BLE协议栈Central 工程中与广播连接建立的事件
- ble学习笔记十四---------ble协议栈之按键事件
- BLE之Central类介绍
- ble学习笔记八---------ble协议栈之简介
- ble学习笔记十一-----------ble协议栈之led试验
- ble协议栈cc2540x-1.3.2之通过key处理过程看任务、事件、消息机制
- BLE 协议栈 之"消息传递""事件触发"谁与争锋
- ble协议栈cc2540x-1.3.2之通过key处理过程看任务、事件、消息机制
- BLE 协议栈之框架解析
- BLE协议栈之OSAL初探
- BLE协议栈之串口数据收发
- BLE协议栈之蓝牙4.2版本
- BLE 协议栈之 主机透传
- BLE 协议栈之RTC时钟
- BLE 协议栈 之看门狗应用
- BLE 协议栈之低功耗管理
- BLE 协议栈 之串口收发
- 3g android4 移植 飞思卡尔i.MX 6Quad Android 4.2.2的中兴和Ublox 3G驱动移植 Android——4.2 - 3G移植之路之 reference-ril .p
- ubuntu14.04 无线热点开启
- Linux进程间通信——使用共享内存
- 解决连接不上mysql,且服务列表里面没有mysql
- awk基础用法
- BLE协议栈之Central事件慢慢谈
- 创造力
- 全局变量、局部变量(auto局部变量)、静态全局变量、静态局部变量的区别
- 蓝桥 算法提高 道路和航路
- oralce-rman-1RMAN Catalog 和 Nocatalog 的区别
- jmeter interface test
- java和js中的正则表达式入门和应用
- 造轮子之我见
- C语言写CGI程序【转】