WinCE蓝牙应用的实现--蓝牙耳机

来源:互联网 发布:java获取dll版本号 编辑:程序博客网 时间:2024/05/01 22:25

蓝牙耳机功能,也就是bluetooth headset /headfree profile,实现起来比想象的复杂.早期的蓝牙规范只定义了headsetprofile, headset的实现原理,是在hci层之上扩展一个接口,传输sco同步面向连接的音频数据包.限定音频流只能是单声道8k的话音级别的pcm. 随着需求发展,明显已经不能满足了,于是又补充了a2dp协议.a2dp协议在l2cap上层,使用sbc压缩并使用acl异步数据包传输,可以支持cd级别的音频流.但是wince5并不支持a2dp,wince6才有.上面2种都是透过hci层来传送音频流,这意味着还要受到hci总线带宽的限制.hci接口常见的有uart,spi,usb.为了突破这个限制,有一些设备会使用独立的pcm总线来传音频流.比如csr的芯片就有独立的pcm总线.我们的设计中,将蓝牙芯片的pcm接到了音频芯片的pcm,这提供了最大的灵活性.

如果你想实现headset,那么就要使用AG(audio gateway)服务btagsvc.dll,并且创建一个蓝牙音频驱动btscosnd.dll.在你的应用中使用DeviceIoControl发送IOCTL_AG_OPEN_AUDIOAG服务,继而,AG服务会建立sco连接并使用waveOutMessage()发送WODM_BT_SCO_AUDIO_CONTROL给蓝牙音频驱动.蓝牙音频驱动于是建立了对hci层的连接,透过参数告知hci要处理的是sco数据,最后创建了一个线程处理sco的事件.

这个过程不会很顺利,一般会遇到一些问题.尤其是自己板上已经有另外一个音频设备的时候.google中搜索你会体会到很多人在解决这个坎坷的问题.哪些问题呢?假设板载的音频设备是device0,在透过wave api来使用驱动时候,希望使用device1,却无法成功.这个问题是微软造成的.上面提到AG会使用waveOutMessage发消息给音频驱动,,waveOutMessage的发送对象竟然是固定的0.也就是device0.所以这限制了蓝牙音频驱动必须是device0.如何决定谁成为device0?并不是注册表中的Index,那只是决定了WAV0还是WAV1.答案是order.因此,本质就是,第一个被加载的音频驱动才是device0.

通过以上方法,成功在wince5上实现了蓝牙headset profile.但是音质的确不很满意.

原创粉丝点击