BD-SDMAC Bluetooth Update - Now BT 5.0 Compatible

Published on May 15, 2020

We are pleased to announce that our BD-SDMAC Wifi + BT module is now Bluetooth 5.0 Compatible!

We have updated our qcacld-2.0 driver and qca-firmware in order to support this. Our latest Yocto Zeus images already have this support included.

Testing/Validation of Bluetooth 5.0

In order to test/validate BT 5.0 with the BD-SDMAC we will do the following:

  • Setup Yocto Image to enable testing tools
  • Bring up the Bluetooth interface (hci0)
  • Confirm BT 5.0 version
  • Test pairing/connecting to BT 5.0 compatible device
  • Test data transfer with audio streaming.
  • Test BLE using gatttool

Test Setup

Nitrogen8M Mini with a BD-SDMAC module running Yocto 3.0 Zeus

Kernel Revision: 4.14.x_2.0.0_ga

Bluetooth Test Devices:

  • iPhone 8
  • JBL Flip 4 Bluetooth Speaker
  • Windows 10 PC

Note that we are testing with Nitrogen8M Mini, but this testing applies to all platforms with the BD-SDMAC.

Also note that in this post we are testing using Yocto, but just know that similar testing applies to other Linux OSs as well. 

Setup Yocto Image to enable Bluetooth audio streaming

We need to make one modification to the Yocto Zeus build in order to enable audio streaming.

Assuming you have followed the Build Procedure in our Yocto 3.0 Zeus post, we need to add pulseaudio as a DISTRO_FEATURE in local.conf. 

DISTRO_FEATURES_append = " pulseaudio"

Now we will build and flash the image are ready to test.

Bring up Bluetooth Interface

We will initialize the interface using our handy silex-uart script.

root@<MACHINE>:~# /usr/share/silex-uart/ start Starting silex-uart rfkill on/off cycle. silex found

Then, we will bring up the interface using hciconfig.

root@<MACHINE>:~# hciconfig hci0 up

Confirm BT 5.0 Version

We can now confirm the module is using BT 5.0 firmware using hciconfig

root@nitrogen8mm:~# hciconfig -a hci0: Type: Primary Bus: UART BD Address: E0:4F:43:44:95:3B ACL MTU: 1024:7 SCO MTU: 60:8 UP RUNNING RX bytes:1363 acl:0 sco:0 events:75 errors:0 TX bytes:1193 acl:0 sco:0 commands:75 errors:0 Features: 0xff 0xfe 0x8f 0xfe 0xd8 0x3f 0x5b 0x87 Packet type: DM1 DM3 DM5 DH1 DH3 DH5 HV1 HV2 HV3 Link policy: RSWITCH HOLD SNIFF Link mode: SLAVE ACCEPT Name: 'nitrogen8mm' Class: 0x200000 Service Classes: Audio Device Class: Miscellaneous, HCI Version: 5.0 (0x9) Revision: 0x0 LMP Version: 5.0 (0x9) Subversion: 0x25a Manufacturer: Qualcomm (29)

The LMP version denotes that we are using Bluetooth 5.0

Test Pairing/Connecting

In this example, we will pair an iPhone using bluetoothctl

Start bluetoothctl.

root@nitrogen8mm:~# bluetoothctl Agent registered [bluetooth]#

Start scanning.

[bluetooth]# scan on Discovery started [NEW] Device AA:BB:CC:DD:EE:FF Iphone [bluetooth]#

Grab MAC of iPhone and pair.

[bluetooth]# pair AA:BB:CC:DD:EE:FF Attempting to pair with AA:BB:CC:DD:EE:FF [CHG] Device AA:BB:CC:DD:EE:FF Connected: yes Request confirmation

Verify passkey on both ends.

[agent] Confirm passkey 141814 (yes/no): yes [CHG] Device AA:BB:CC:DD:EE:FF Modalias: bluetooth:... [CHG] Device AA:BB:CC:DD:EE:FF UUIDs: .... [CHG] Device AA:BB:CC:DD:EE:FF ServicesResolved: yes [CHG] Device AA:BB:CC:DD:EE:FF Paired: yes Pairing successful

Trust this device.

[bluetooth]# trust AA:BB:CC:DD:EE:FF [CHG] Device AA:BB:CC:DD:EE:FF Trusted: yes Changing AA:BB:CC:DD:EE:FF trust succeeded

Finally, connect to the device.

[bluetooth]# connect AA:BB:CC:DD:EE:FF Attempting to connect to AA:BB:CC:DD:EE:FF [CHG] Device AA:BB:CC:DD:EE:FF Connected: yes Connection successful [CHG] Device AA:BB:CC:DD:EE:FF ServicesResolved: yes [Iphone]#

Test Data Transfer With Audio Streaming

For testing audio streaming, we need use pulseaudio and must start it before bringing the Bluetooth interface up. 

After bootup start pulseaudio as a daemon (you can ignore the error message it prints).

root@nitrogen8mm:~# pulseaudio -D W: [pulseaudio] main.c: This program is not intended to be run as root (unless --system is specified).

Next, load a couple modules required for Bluetooth audio streaming using pactl.

root@nitrogen8mm:~# pactl load-module module-bluetooth-discover 18 root@nitrogen8mm:~# pactl load-module module-switch-on-connect 20

Now you can bring up the interface as directed above and connect either a slave device such a Bluetooth speaker to stream audio to, or connect to a master device like a phone or PC to stream audio from and play through the boards speakers. 

If pairing to a master device, after connection the Nitrogen device will show up as speakers to play audio to.

For example here is how the Nitrogen device shows up on a Windows 10 PC when we do the above steps. 

If pairing to a slave device to stream audio to, there a couple more steps required. In this example we will use a JBL Flip 4 Bluetooth speaker.

After doing the above steps to start pulseaudio and connect to the speaker, lets make sure its available as a sink for playing audio once again using pactl.

root@nitrogen8mm:~# pactl list sinks Sink #0 State: SUSPENDED Name: alsa_output.platform-sound-wm8960.analog-mono Description: Built-in Audio Analog Mono Driver: module-alsa-card.c Sample Specification: s16le 1ch 44100Hz Channel Map: mono Owner Module: 6 Mute: no Volume: mono: 52057 / 79% / -6.00 dB balance 0.00 Base Volume: 52057 / 79% / -6.00 dB Monitor Source: alsa_output.platform-sound-wm8960.analog-mono.monitor Latency: 0 usec, configured 0 usec Flags: HARDWARE HW_VOLUME_CTRL DECIBEL_VOLUME LATENCY Properties: alsa.resolution_bits = "16" device.api = "alsa" device.class = "sound" alsa.class = "generic" alsa.subclass = "generic-mix" = "" = "HiFi wm8960-hifi-0" alsa.subdevice = "0" alsa.subdevice_name = "subdevice #0" alsa.device = "0" alsa.card = "0" alsa.card_name = "wm8960-audio" alsa.long_card_name = "wm8960-audio" device.bus_path = "platform-sound-wm8960" sysfs.path = "/devices/platform/sound-wm8960/sound/card0" device.form_factor = "internal" device.string = "hw:0" device.buffering.buffer_size = "8816" device.buffering.fragment_size = "2204" device.access_mode = "mmap" = "analog-mono" device.profile.description = "Analog Mono" device.description = "Built-in Audio Analog Mono" module-udev-detect.discovered = "1" device.icon_name = "audio-card" Ports: analog-output-speaker: Speakers (priority: 10000) analog-output-headphones: Headphones (priority: 9000, not available) Active Port: analog-output-speaker Formats: pcm Sink #1 State: SUSPENDED Name: bluez_sink.00_42_79_A1_96_30.a2dp_sink Description: JBL Flip 4 Driver: module-bluez5-device.c Sample Specification: s16le 2ch 44100Hz Channel Map: front-left,front-right Owner Module: 21 Mute: no Volume: front-left: 65536 / 100% / 0.00 dB, front-right: 65536 / 100% / 0.00 dB balance 0.00 Base Volume: 65536 / 100% / 0.00 dB Monitor Source: bluez_sink.00_42_79_A1_96_30.a2dp_sink.monitor Latency: 0 usec, configured 0 usec Flags: HARDWARE DECIBEL_VOLUME LATENCY Properties: bluetooth.protocol = "a2dp_sink" device.description = "JBL Flip 4" device.string = "00:42:79:A1:96:30" device.api = "bluez" device.class = "sound" device.bus = "bluetooth" device.form_factor = "speaker" bluez.path = "/org/bluez/hci0/dev_00_42_79_A1_96_30" bluez.class = "0x240414" bluez.alias = "JBL Flip 4" device.icon_name = "audio-speakers-bluetooth" Ports: speaker-output: Speaker (priority: 0) Active Port: speaker-output Formats: pcm

As you can see the JBL Flip 4 shows up as Sink #1. Now lets stream some audio to it.

Grab the "Name:" Field from Sink #1 above and set it as pulseaudio's default sink.

root@nitrogen8mm:~# pactl set-default-sink bluez_sink.00_42_79_A1_96_30.a2dp_sink

Now play any .wav file using paplay

root@nitrogen8mm:~# paplay test.wav

Validate the audio is playing, and now we have successfully validated data transfer via audio streaming using BT 5.0.

BLE Testing using gatttool 

gatttool is a handy tool for testing BLE devices. Instead of reinventing the wheel in terms of instructions for use, please instead use this post as a helpful guide for using the tool.

There you have it, we have provided a good validation of Bluetooth 5.0 on our BD-SDMAC BT module. 


If you have any issues, please email