1. 精讲蓝牙协议栈(Bluetooth Stack):SPP/A2DP/AVRCP/HFP/PBAP/IAP2/HID/MAP/OPP/PAN/GATTC/GATTS/HOGP等协议理论
2. 欢迎大家关注和订阅,【蓝牙协议栈】和【Android Bluetooth Stack】专栏会持续更新中.....敬请期待!
目录
1. 协议架构
1.1 Profile Dependencies
1.2 HFP Protocol Stack
2. HFP功能支持情况
3. 通话过程协议分析
3.1 拨打电话 - AG
3.1.1 报告状态
3.1.2 选取编码方式
3.1.3 拨号
3.1.5 响铃
3.1.6 通话
3.2 拨打电话 - HF
3.2.1 推送号码
1. 协议架构
1.1 Profile Dependencies
在蓝牙电话的数据传输中使用的是SCO协议(同步定向链接)。支持对时延敏感的信息如语音。
使用保留带宽进行同步通信,即两台设备在LMP层利用保留时隙在物理信道上周期传送数据包,这种类型的链接主要用于传送SCO包(语音数据)。SCO不包括CRC码,且不进行重传,主要支持传输有时间限制的信息,例如声音。
仅仅在ACL链接已经建立之后,才可以建立SCO链接;
-
AT CMD:AT指令是应用于终端设备和PC应用之间的连接与通信的指令;
-
SPP:蓝牙串口协议,在蓝牙设备之间建立虚拟的串口进行数据通信,简单的说就是两个蓝牙设备对端发送自定义数据;iPhone不支持SPP协议;
-
GAP:通用访问配置文件,该Profile保证不同的Bluetooth产品可以互相发现对方并建立连接;GAP定义了蓝牙设备如何发现和建立与其他设备的安全/不安全连接,它处理一些一般模式的业务(询问、命名和搜索)和一些安全性问题;GAP一般有4个作用:
- Profile Role
- 可发现模式和过程
- 连接模式和过程
- 安全模式和过程
-
eSCO:可以简单的理解为和SCO不同点:支持数据包的重传;
-
incoming call:由Phone Network到AG的通话,即称为来电;
-
outgoing call:由AG到Phone Network的通话,即称为拨号,去电;
1.2 HFP Protocol Stack
针对蓝牙电话,涉及到的协议有:HFP、RFCOMM;
目前HFP的使用场景常见的有车载蓝牙、耳机、PDA(Personal Digital Assistant - 掌上电脑,类似于智能手机、平板电脑、手持游戏机等),其中HFP协议中定义了AG和HFP两种角色:
- AG(Audio Gate):音频网关 - 音频设备输入输出网关;
- HF(Hands Free):免提 - 该设备作为音频网关的远程音频输入 / 输出机制,并可提供若干遥控功能;
在车载领域,手机侧为AG,车载侧为HF,在Android源码定义中,通常将AG称为HFP/AG,将HF称为HFPClient/HF;
2. HFP功能支持情况
(M代表强制支持,O代表可选)
Num | function | HF | AG | Num | function | HF | AG |
---|---|---|---|---|---|---|---|
1 | 连接管理 | M | M | 14 | 噪声抑制回声消除 | O | O |
2 | 电话状态信息 | M | M | 15 | 语音识别 | O | O |
3 | 音频连接处理 | M | M | 16 | 号码绑定语音标签 | O | O |
4 | 接收语音来电 | M | M | 17 | 传输多音频能力 | O | M |
5 | 拒绝语音来电 | M | O | 18 | 远程音量控制 | O | O |
6 | 中断电话 | M | M | 19 | 回复和保持 | O | O |
7 | 通话中音频链路切换 | M | M | 20 | 描述号码信息 | O | M |
8 | 免提设备拨号 | O | M | 21a | 扩展电话状态 | O | M |
9 | 历史列表拨号 | O | M | 21b | 扩展电话控制 | O | O |
10 | 拨打最后一个电话 | O | M | 22 | 特有指示 | O | M |
11 | 拨号等待通知 | O | M | 23 | 宽频语音 | O | O |
12 | 三方通话 | O | O | 24 | 编解码器协商 | O | O |
13 | CLI(呼叫线路识别) | O | M | 25 | 手持设备指示器 | O | O |
3. 通话过程协议分析
上述过程中,描述的都是在非通话状态下的 AT+ 指令的状态信息,接下来我们对通话状态过程中涉及到的AT指令状态信息进行描述;
3.1 拨打电话 - AG
拨打电话大体分为拨号、响铃、通话这三个部分,状态变化后AG侧都会主动通知HF侧,HF侧再通过“AT+CLCC”获取详细的电话参数信息。
3.1.1 报告状态
+CIEV
用于报告事件状态;
Bluetooth HFP Profile
[Role: AG - Audio Gate (1)]
AT Stream: \r\n+CIEV: 2,2\r\n
Command 0: +CIEV
Command: +CIEV (Indicator Events Reporting)
Type: Response (0x003a)
Parameters
Indicator Index: 2
Indicator 2: 2
+CIEV: ,
-
:Indicator,该值对应了AT+CIND指令的中index,例如
- 1:call
- 2:callsetup
- 3:service
- 4:signal
- 5:roam
- 6:battchg
- 7:callheld
-
:指定的就是Indicator指示对应的value值;
-
例如,call = 1
- 0: 没有电话在进行中
- 1:至少有一个电话在进行中
-
Indicator参数常见的几种配置:
- +CIEV:1,1:接听电话
- +CIEV:2,0:当前没有等待的电话需要处理
- +CIEV:2,2:拨打电话
- +CIEV:2,3:已拨通
当前的状态为拨打电话状态;
3.1.2 选取编码方式
+BCS & AT+BCS
Bluetooth HFP Profile
[Role: AG - Audio Gate (1)]
AT Stream: \r\n+BCS: 2\r\n
Command 0: +BCS
Command: +BCS (Bluetooth Codec Selection)
Type: Response (0x003a)
Parameters
Codec: mSBC (2)
当前选用的编解码器为mSBC,AT+BAC指令用于获取蓝牙可用编解码器,而对应的AT+BCS指令用于指定使用哪种编解码器;
Bluetooth HFP Profile
[Role: HS - Headset (2)]
AT Stream: AT+BCS=2\r
Command 0: +BCS
Command Line Prefix: AT
Command: +BCS (Bluetooth Codec Selection)
Type: Action Command (0x003d)
Parameters
Codec: mSBC (2)
然后返回对应的OK Response;
3.1.3 拨号
AT+CLCC & +CLCC
Bluetooth HFP Profile
[Role: HS - Headset (2)]
AT Stream: AT+CLCC\r
Command 0: +CLCC
Command Line Prefix: AT
Command: +CLCC (Current Calls)
Type: Action Command (0x000d)
Parameters: No
Bluetooth HFP Profile
[Role: AG - Audio Gate (1)]
AT Stream: \r\n+CLCC: 1,0,2,0,0,"03511008611",129\r\n
Command 0: +CLCC
Command: +CLCC (Current Calls)
Type: Response (0x003a)
Parameters
ID: 1
Direction: Mobile Originated (0)
State: Dialing (2)
Mode: Voice (0)
Mpty: Call is not one of multiparty (conference) call parties (0)
Number: "03511008611"
Type: The phone number format may be a national or international format, and may contain prefix and/or escape digits. No changes on the number presentation are required. (129)
拨号状态下,State = 2,Dialing;
对应上层回调信息:
01-01 00:03:27.361 1655 1758 D NativeInterface: onCallSetup: addr [B@5e15405 device30:AA:E4:42:C7:DD
01-01 00:03:27.361 1655 1758 D NativeInterface: onCallSetup: address [B@5e15405 event StackEvent {type:EVENT_TYPE_CALLSETUP, value1:2, value2:0, value3:0, value4:0, string: "null", device:30:AA:E4:42:C7:DD}
然后返回对应的OK Response;
同步连接请求
Frame 630: 67 bytes on wire (536 bits), 67 bytes captured (536 bits)
Bluetooth
[Source: host]
[Destination: controller]
Bluetooth HCI H4
[Direction: Sent (0x00)]
HCI Packet Type: HCI Command (0x01)
Bluetooth HCI Command - Enhanced Accept Synchronous Connection Request
Command Opcode: Enhanced Accept Synchronous Connection Request (0x043e)
0000 01.. .... .... = Opcode Group Field: Link Control Commands (0x01)
.... ..00 0011 1110 = Opcode Command Field: Enhanced Accept Synchronous Connection Request (0x03e)
Parameter Total Length: 63
BD_ADDR: HuaweiDe_42:c7:dd (30:aa:e4:42:c7:dd)
Tx Bandwidth (bytes/s): 8000
Rx Bandwidth (bytes/s): 8000
Transmit Coding Format
Codec: mSBC (0x05)
Company ID: Ericsson Technology Licensing (0x0000)
Vendor Codec ID: 0x0000
Receive Coding Format
Codec: mSBC (0x05)
Company ID: Ericsson Technology Licensing (0x0000)
Vendor Codec ID: 0x0000
Transmit Codec Frame Size: 60
Receive Codec Frame Size: 60
Input Bandwidth: 32000
Output Bandwidth: 32000
Input Coding Format
Codec: Linear PCM (0x04)
Company ID: Ericsson Technology Licensing (0x0000)
Vendor Codec ID: 0x0000
Output Coding Format
Codec: Linear PCM (0x04)
Company ID: Ericsson Technology Licensing (0x0000)
Vendor Codec ID: 0x0000
Input Coded Data Size: 16
Output Coded Data Size: 16
Input PCM Data Format: 2's complement (0x02)
Output PCM Data Format: 2's complement (0x02)
Input PCM Sample Payload MSB Position: 0
Output PCM Sample Payload MSB Position: 0
Input Data Path: Vendor Specific
Output Data Path: Vendor Specific
Input Transport Unit Size: 0
Output Transport Unit Size: 0
Max. Latency (ms): 13
Packet Type: 0x0388, 3-EV5 may NOT be used, 2-EV5 may NOT be used, 3-EV3 may NOT be used, EV3 may be used
0000 00.. .... .... = Reserved: 0x00
.... ..1. .... .... = 3-EV5 may NOT be used: True
.... ...1 .... .... = 2-EV5 may NOT be used: True
.... .... 1... .... = 3-EV3 may NOT be used: True
.... .... .0.. .... = 2-EV3 may NOT be used: False
.... .... ..0. .... = EV5 may be used: False
.... .... ...0 .... = EV4 may be used: False
.... .... .... 1... = EV3 may be used: True
.... .... .... .0.. = HV3 may be used: False
.... .... .... ..0. = HV2 may be used: False
.... .... .... ...0 = HV1 may be used: False
Retransmission Effort: At least 1 retransmission, optimize for link quality (2)
[Pending in frame: 631]
[Command-Pending Delta: 3.244ms]
[Response in frame: 632]
[Command-Response Delta: 117.981ms]
- Source:host,蓝牙协议层
- Destination:蓝牙协议芯片
- Direction:Sent(0x00):类型 sent,对应的为Rcvd(0x01)
- HCI Packet Type:HCI Command,这个类型是host和Controller通信使用的方式,对应的Controller向上回调给Host的方式为HCI Event;
- BD_ADDR:AG侧蓝牙设备
- Codec:mSBC(0x05),编解码器
- Codec:Linear PCM (0x04),音频格式
- Command in frame: 630
- Pending in frame:631
- Response in frame:632
Frame 631: 7 bytes on wire (56 bits), 7 bytes captured (56 bits)
Bluetooth
[Source: controller]
[Destination: host]
Bluetooth HCI H4
[Direction: Rcvd (0x01)]
HCI Packet Type: HCI Event (0x04)
Bluetooth HCI Event - Command Status
Event Code: Command Status (0x0f)
Parameter Total Length: 4
Status: Pending (0x00)
Number of Allowed Command Packets: 1
Command Opcode: Enhanced Accept Synchronous Connection Request (0x043e)
0000 01.. .... .... = Opcode Group Field: Link Control Commands (0x01)
.... ..00 0011 1110 = Opcode Command Field: Enhanced Accept Synchronous Connection Request (0x03e)
[Command in frame: 630]
[Response in frame: 632]
[Command-Pending Delta: 3.244ms]
[Pending-Response Delta: 114.737ms]
- Direction:Rcvd (0x01)
- Command in frame: 630
- Response in frame:632
Frame 632: 20 bytes on wire (160 bits), 20 bytes captured (160 bits)
Bluetooth
[Source: controller]
[Destination: host]
Bluetooth HCI H4
[Direction: Rcvd (0x01)]
HCI Packet Type: HCI Event (0x04)
Bluetooth HCI Event - Synchronous Connection Complete
Event Code: Synchronous Connection Complete (0x2c)
Parameter Total Length: 17
Status: Success (0x00)
Connection Handle: 0x0003
BD_ADDR: HuaweiDe_42:c7:dd (30:aa:e4:42:c7:dd)
Link Type: eSCO connection (0x02)
Transmit Interval: 12 slots (7.5 msec)
Retransmit Window: 6 slots (3.75 msec)
Rx Packet Length: 60
Tx Packet Length: 60
Air Mode: Unknown (5)
[Command in frame: 630]
[Pending in frame: 631]
[Pending-Response Delta: 114.737ms]
[Command-Response Delta: 117.981ms]
- Link Type:eSCO connection (0x02),eSCO通道已连接成功,因为我们选用的是mSBC编解码器,而mSBC编解码器只支持eSCO链路;
同步连接成功之后,底层会向上层回调onAudioStateChanged:
01-01 00:03:27.808 1655 1928 D bt_btif : bta_hf_client_sco_conn_cback: 0
01-01 00:03:27.808 1655 1928 I bt_btif : bta_sys_event: Event 0x1b0c
01-01 00:03:27.808 1655 1928 D bt_btif : bta_hf_client_hdl_event: BTA_HF_CLIENT_SCO_OPEN_EVT (0x1b0c)
01-01 00:03:27.808 1655 1928 I bt_btif : HF Client evt : State 2 (BTA_HF_CLIENT_OPEN_ST), Event 0x1b0c (BTA_HF_CLIENT_SCO_OPEN_EVT)
01-01 00:03:27.808 1655 1928 D bt_btif : bta_hf_client_sco_conn_open
01-01 00:03:27.808 1655 1928 D bt_btif : bta_hf_client_sco_event: before state: 2 event: 4
01-01 00:03:27.808 1655 1928 D bt_btif : bta_hf_client_sco_event: after state: 4
01-01 00:03:27.808 1655 1928 D bt_btif : bta_dm_pm_cback: st(4), id(27), app(1)
01-01 00:03:27.808 1655 1928 D bt_btif : bta_dm_pm_stop_timer:
01-01 00:03:27.808 1655 1928 D bt_btif : bta_dm_pm_cback bta_dm_pm_stop_timer for current service, restart other service timers: count = 3
01-01 00:03:27.808 1655 1928 D bt_btm : btm_bda_to_acl found
01-01 00:03:27.808 1655 1928 D bt_btm : BTM_ReadRemoteFeatures
01-01 00:03:27.808 1655 1928 D bt_btif : bta_dm_pm_cback: SCO inactive, reset SSR to zero
01-01 00:03:27.808 1655 1928 D bt_btif : bta_dm_pm_set_mode: srvcsid: 18, state: 0, j: 5
01-01 00:03:27.808 1655 1928 D bt_btif : bta_dm_pm_set_mode: srvcsid: 27, state: 4, j: 21
01-01 00:03:27.808 1655 1928 D bt_btif : bta_dm_pm_set_mode: srvcsid: 26, state: 6, j: 16
01-01 00:03:27.808 1655 1928 D bt_btif : bta_dm_pm_set_mode dm_pm_timer:0, 7000 ms
01-01 00:03:27.808 1655 1928 D bt_btif : bta_dm_pm_set_mode dm_pm_timer:1, 7000 ms
01-01 00:03:27.808 1655 1928 D bt_btif : bta_dm_pm_set_mode dm_pm_timer:2, 7000 ms
01-01 00:03:27.808 1655 1928 D bt_btif : bta_dm_pm_set_mode dm_pm_timer:3, 7000 ms
01-01 00:03:27.808 1655 1928 D bt_btif : bta_dm_pm_set_mode dm_pm_timer:4, 7000 ms
01-01 00:03:27.808 1655 1928 D bt_btif : bta_dm_pm_set_mode dm_pm_timer:5, 7000 ms
01-01 00:03:27.808 1655 1928 D bt_btif : bta_dm_pm_set_mode dm_pm_timer:6, 7000 ms
01-01 00:03:27.808 1655 1928 D bt_btif : btif_transfer_context event 6, len 52
01-01 00:03:27.809 1655 1758 D bt_btif : btif task fetched event a001
01-01 00:03:27.809 1655 1758 D bt_btif : btif_context_switched
01-01 00:03:27.809 1655 1758 D bt_btif : btif_hf_client_upstreams_evt: event=BTA_HF_CLIENT_AUDIO_MSBC_OPEN_EVT (6)
01-01 00:03:27.809 1655 1758 I bt_btif : btif_hf_client_upstreams_evt: HAL bt_hf_client_callbacks->audio_state_cb
01-01 00:03:27.810 1655 1758 D NativeInterface: onAudioStateChanged: address [B@ed64403 event StackEvent {type:EVENT_TYPE_AUDIO_STATE_CHANGED, value1:3, value2:0, value3:0, value4:0, string: "null", device:30:AA:E4:42:C7:DD}
表明当前Audio Channel已开启,上层可以根据Audio State执行一些相应的逻辑;
3.1.5 响铃
+CIEV
Bluetooth HFP Profile
[Role: AG - Audio Gate (1)]
AT Stream: \r\n+CIEV: 2,3\r\n
Command 0: +CIEV
Command: +CIEV (Indicator Events Reporting)
Type: Response (0x003a)
Parameters
Indicator Index: 2
Indicator 2: 3
callsetup = 3,代表了呼叫的对方正在响铃,对应实际场景为:03511008611号码正在响铃中;
AT+CLCC & +CLCC
Bluetooth HFP Profile
[Role: HS - Headset (2)]
AT Stream: AT+CLCC\r
Command 0: +CLCC
Command Line Prefix: AT
Command: +CLCC (Current Calls)
Type: Action Command (0x000d)
Parameters: No
Bluetooth HFP Profile
[Role: AG - Audio Gate (1)]
AT Stream: \r\n+CLCC: 1,0,3,0,0,"03511008611",129\r\n
Command 0: +CLCC
Command: +CLCC (Current Calls)
Type: Response (0x003a)
Parameters
ID: 1
Direction: Mobile Originated (0)
State: Alerting (3)
Mode: Voice (0)
Mpty: Call is not one of multiparty (conference) call parties (0)
Number: "03511008611"
Type: The phone number format may be a national or international format, and may contain prefix and/or escape digits. No changes on the number presentation are required. (129)
拨号状态下,State = 3,Alerting;
然后返回对应的OK Response;
3.1.6 通话
+CIEV
Bluetooth HFP Profile
[Role: AG - Audio Gate (1)]
AT Stream: \r\n+CIEV: 1,1\r\n
Command 0: +CIEV
Command: +CIEV (Indicator Events Reporting)
Type: Response (0x003a)
Parameters
Indicator Index: 1
Indicator 1: 1
call = 1,代表了至少有一个正在通话中,对应实际场景为:03511008611号码已拨通;
+CIEV
Bluetooth HFP Profile
[Role: AG - Audio Gate (1)]
AT Stream: \r\n+CIEV: 2,0\r\n
Command 0: +CIEV
Command: +CIEV (Indicator Events Reporting)
Type: Response (0x003a)
Parameters
Indicator Index: 2
Indicator 2: 0
callsetup = 0,代表当前没在呼叫,对应实际场景为:03511008611号码已拨通,呼叫状态变为了已拨通状态;
AT+CLCC & +CLCC
Bluetooth HFP Profile
[Role: HS - Headset (2)]
AT Stream: AT+CLCC\r
Command 0: +CLCC
Command Line Prefix: AT
Command: +CLCC (Current Calls)
Type: Action Command (0x000d)
Parameters: No
Bluetooth HFP Profile
[Role: AG - Audio Gate (1)]
AT Stream: \r\n+CLCC: 1,0,0,0,0,"03511008611",129\r\n
Command 0: +CLCC
Command: +CLCC (Current Calls)
Type: Response (0x003a)
Parameters
ID: 1
Direction: Mobile Originated (0)
State: Active (0)
Mode: Voice (0)
Mpty: Call is not one of multiparty (conference) call parties (0)
Number: "03511008611"
Type: The phone number format may be a national or international format, and may contain prefix and/or escape digits. No changes on the number presentation are required. (129)
拨号状态下,State = 3,Alerting;
然后返回对应的OK Response;
3.2 拨打电话 - HF
HF侧的拨打电话和AG侧比较起来就多了一个步骤,通过AT命令“ATD”将需要拨打的电话信息发送到AG侧,然后通过手机的电话模块呼出电话;
3.2.1 推送号码
ATDddd..dd:标准AT命令,用于HF侧发送拨打电话号码至AG侧;
Bluetooth HFP Profile
[Role: HS - Headset (2)]
AT Stream: ATD03511008611;\r
Command 0: D
Command Line Prefix: AT
Command: D (Dial)
[Expert Info (Warning/Protocol): Non mandatory type or command in this role]
[Non mandatory type or command in this role]
[Severity level: Warning]
[Group: Protocol]
Parameters: No
对应的Response为OK;