Dual Split A2dp SBC Streams

背景

SBC是经典蓝牙A2DP强制支持的音频标准配置的codec,通常情况下,在我们的印象中SBC是蓝牙低质量音质的代名词,如果一个耳机或者音响只支持SBC一个codec,那么这个耳机或音响肯定是低端货,一般高端的人耳机都会支持一些其他私有编码器,比如AAC,LDAC,还有各家公司自己开发的编解码器,比如高通的APTX,华为自己开发的L2HC等等。其实不然,蓝牙音频SBC是可以通过一些方法来提升音质,甚至可以提升至APTX HD相当的音效。

记得大概七八年前,我在上一家公司曾经做过一个韩国某司的智能TV项目,因为当时开发调试的时间比较长,所以还有印象就是当时客户就要求我们基于bluedroid蓝牙协议栈架构的A2DP Source端做如下修改:

  1. 左右音响需要单独建立ACL & A2DP链路,从audio系统那边过来的立体声数据按Left-Right-Left-Right组合,需要在协议栈里做分离,Left Channel的数据只发送Left Speaker,Right Channel的数据发送Right Speaker。
  2. 左右声道的音频数据都是在协议栈里分别各自进行SBC Encode,各自有独立的编码参数, Channel Mode由原来的Joint stereo 变成了Mono Channel Mode。
  3. A2DP configuration能够动态配置,比如单独一个音响的时候是aptx Mode,如果有两个音响,则需要切换为SBC,反之亦然。
  4. 需要给应用层提供一些接口,比如配置左右音响,配置bitpool的值等等。

上面的需求看似不复杂,其实当时一个人还是花了不少时间,尤其是两条数据流同时做SBC encode的时候,SBC的库还有重入的问题(其实就是SBC编码库引入一些全局变量导致),后面又碰到一些两个音响数据流同步等问题,还有两条流变一条流,一条流变两条流做A2DP Configuration动态切换问题等等。

客户为啥需要这么做呢?这么配置会带来哪些好处,接下来探讨:

SBC编码参数

下面看一个具体耳机端实例所支持的SBC编码的参数:
在这里插入图片描述

参数详解
Channel Mode联合立体声,立体声,双通道,单通道Dual channel:由两个单声道组成,两个声道编码时不考虑相关性,每个声道的码率为音频总码率的一半。
Stereo:由两个或多个相互独立的声道组成,每个声道的码率根据其各自编码信息量大小而定。人耳听到时能对音源位置进行定位。E.G right use 48kbits and left uses 96 kbits in a 128kbits file。不会计算双声道之间的资料相关性,但是会协调分配双声道的资料流量,自动分配较多的 Bit 给复杂的声道使用。
Joint stereo:也是由两个声道组成,但编码时兼顾了这两个声道的共同信息量,比Stereo的压缩率更高。在这个压缩模式下,LAME 会利用双声道之间的资料相关性进行演算。左右声道资料类似时,会利用 M/S (Mid/Side) 编码技术,计算中央声道 (L+R) 和两侧声道差异 (L-R) 的值,并且会分配较多的 Bit 给中央声道,增加资料记录频宽。
Sampling Frequency48KHZ,44.1KHZ音频采样率,可以理解为1秒播放44100个采样点或者48000个采样点
Allocation MethodLoudness或SNR量化分配方法是响度还是信噪比
sub bands8或者4"Number of frequency bands"指的是频率带的数量。通常用于音频处理、无线通信等领域,表示将整个频率范围分割成的多个区段或通道的数量。每个频带代表一个特定范围内的频率集合。例如,在音频均衡器中,不同的频带可以分别调整不同频率范围的声音强度。在无线通信中,频带则指定了信号传输所使用的具体频率区间。
Block Length4,8,12,16一个音频帧中的音频块数据
Min Bitpool value2量化比特池的最小值为2
Max Bitpool Value39量化比特池的最大值为39

下面看一个手机通过AVDTP Set Configuration设置的SBC编码参数的实例:
在这里插入图片描述
可以看到手机选择是:联合立体声,采样率44.1kHz ,响度,频带数量为8,帧中块数为16,量化比特池最小值为2,最大值为39。

SBC码率计算

b i t r a t e = 8 ∗ f r a m e _ l e n g t h ∗ s a m p l e _ r a t e s u b b a n d s ∗ b l o c k s bitrate= \frac{8 * frame\_length * sample\_rate}{subbands * blocks} bitrate=subbandsblocks8frame_lengthsample_rate
其中sample_rate, subbands和blocks这些都是定义好了的,只有frame_length的计算方法参考:
在这里插入图片描述
可以计算上面的手机和耳机传输SBC音频数据的frame_length = 4 + (8 * 2)/2 + (8+16 * 39)/8 = 91

可以计算上面的手机和耳机传输SBC数据的码率为8 * 91 * 44100/(8 * 16)=250.8 kbps

这里也有一个现成的计算方法:https://btcodecs.valdikss.org.ru/sbc-bitrate-calculator/ 来验证一下:
在这里插入图片描述
上面这个表格的2DH5代表,采用2M PHY,一次传输采用5个slot(0.625ms)+一个slot的间隔,总共是6x0.625ms = 3.75ms;
而3DH5则表示采用3M PHY,一次传输采用5个slot +一个slot的间隔,总共也是3.75ms。
可以看到采用2DH5最多一次可以传输679个字节,一个传输周期可以传输7个frame,有25个字节浪费;
计算方法:679 - 4(L2CAP) - 12(AVDTP) - 1(SBC header) - (91 * 7) = 25。
而采用3DH5一次最多传输1021个字节,可以传输11个frame,只有3个字节浪费。
同理:1021 - 4(L2CAP) - 12(AVDTP) - 1(SBC header) - (91* 11) = 3。

这里列举A2DP SPEC定义的高质量和低质量的一些常用的比特池对应的SBC码率表格:
在这里插入图片描述

Dual Split A2dp SBC Streams Benifit

再回到我之前的项目中,假设按照以下的固定配置,每个音频帧包含16块,量化分配方法为响度和频带数为8,比特池为38的设置下,来看看单个A2DP联合立体声音频数据流和两条A2DP MONO音频数据流各自对应的码率为多少:

联合立体声:

  • frame_length = 4 + 8* 2/2 + (8+16*38)/8 = 89 ;
  • bitrate = 8 * 89* 44100/(8*16)=245.3kbps

MONO:

  • frame_length = 4 + 8*2/2 + (16 * 38)/8 = 88
  • bitrate = 8 * 88* 44100/(8*16)=242.5kbps
    这里需要注意的是采用联合立体声的话,如果两个音响配合,另外一个副音响可以采取监听模式,这样蓝牙的总带宽还是245.3kbps;如果采取MONO,两个音响需要建立两条A2DP音频数据流,那么总带宽就变成了242.5 x 2 = 485 kbps。
    带宽翻倍最终带来的也是效果翻倍甚至更好,这是由专业测试的,可以达到Aptx HD的效果,具体参考:http://soundexpert.org/articles/-/blogs/audio-quality-of-sbc-xq-bluetooth-audio-codec
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Tim_Jiangzj

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值