Legacy pairing, SSP - enable from command line [Linux] - bluetooth

As part of my automation project, I have two USB dongles and I need to automate the bluetooth test-cases. Both the devices seem to support SSP. This I infer from the hciconfig output. For ex: typing $hciconfig hci0 sspmode
I get,
hci0: Type: BR/EDR Bus: USB
BD Address: xx:xx:xx:xx:xx:xx ACL MTU: 1021:8 SCO MTU: 64:1
Simple Pairing mode: Enabled
and I get a similar output for hci1. My questions are as follows:
a) How do I make them do SSP from command line [with and without encryption]?
b) How do I make them pair using legacy pairing method from command line [with and without encryption]?
For both #a and #b, how do I validate that indeed SSP and legacy pairing have happened using hcidump [if someone can point me to what to expect from the hci logs, I Would be very thankful.

Related

Enforce bluetooth security and authentication using BlueZ

I'm using BlueZ 5.49 and trying to connect, pair, and pass information between two different bluetooth devices.
It's seems like i have problem with enforcing security and authentication between the two.
I'm configuring each hci device with:
hciconfig hci0 pscan auth encrypt which as i read, is setting the device to security mode 3.
In addition i'm creating manualy this path in both sides: /var/lib/bluetooth/<local_bdaddr>/<remote_bdaddr>/info with LinkKey.
I've noticed that if i'm creating the path for only one device, and then trying to connect using rfcomm connect from the device without the infofile, the connection succeed, even though the device is lacking the info file which containts the LinkKey.
If i'm trying rfcomm connect from the device with the info file i'm getting Key Exchange Error, which is acceptable since the other device doesn't have the key.
My base line is that it seems that security and authentication are not enforced.
Many Thanks,
Liad
Apparently hci device is by default set to work in Secure Simple Pairing also known
as sspmode. Simple Pairing originaly generated to support devices that can't insert pin code during pairing process (such as headset).
Hence when a device is in sspmode enabled, it use a default pin key - say 0000, and then based on the pin, generating LinkKey to encrypt and authenticate, and thus not truely enforcing authentication as i mentioned before.
The line hciconfig hci0 sspmode disable is disabling the Secure Simple Pairing mode, and finally enforce authentication using the static LinkKey you supply
in the info file which located in /var/lib/bluetooth/<your_mac>/<remote_mac>/info.

Can't set fast-connectable on my Bluetooth controller with BlueZ5

I can't set fast-connectable on my Bluetooth controller:
# btmgmt fast-conn on
Set Fast Connectable for hci0 failed with status 0x0c (Not Supported)
though fast-connectable is supported according to btmgmt!
# btmgmt info
Index list with 1 item
hci0: Primary controller
addr 4C:74:03:64:82:1F version 7 manufacturer 15 class 0x000000
supported settings: powered connectable fast-connectable discoverable bondable link-security ssp br/edr hs le advertising secure-conn debug-keys privacy configuration static-addr
current settings: powered connectable bondable le secure-conn
name mybox
short name
hci0: Configuration options
supported options: public-address
missing options:
Same problem if the controller is powered off
# btmgmt power off
before trying to apply fast-connectable...
Would you have any idea why?
I'm running a Linux 4.1.20 kernel, with BlueZ 5.49.
I searched the Internet, the BlueZ documentation, but couldn't find much information about the setting fast-connectable. Help would be appreciated.

Is there a way to find out which Bluetooth device is plugged into which USB port?

I'm using two Bluetooth adaptors with BlueZ, both are the same device but with different types of antenna, is there any method to find out which usb port the identifier on BlueZ (hci0/hci1) is referring to?
I can discover the MAC address of the device through hcitool dev, so if there was a way to discover which USB port the adaptor with that MAC address was connected to, that would also solve my problem.
As both the adaptors are the same model, lsusb does not provide any identifying information I can use.
Using Ubuntu 16.04. I am looking for a solution in any form, whether it is a shell command or java/C/python/etc.
This answer should point you in the right direction, though doesn't give you a complete solution.
You should be able to use the contents of the "sys" filesystem, under /sys/class/bluetooth:
$ ls -lA /sys/class/bluetooth/
total 0
lrwxrwxrwx 1 root root 0 Dec 8 09:35 hci0 -> ../../devices/platform/soc/3f980000.usb/usb1/1-1/1-1.3/1-1.3:1.0/bluetooth/hci0
lrwxrwxrwx 1 root root 0 Dec 8 09:35 hci1 -> ../../devices/platform/soc/3f201000.serial/tty/ttyAMA0/hci1
That's from my Raspberry Pi, with a builtin adapter on the /dev/ttyAMA0 UART interface, and an added Bluetooth adapter on USB. The information in the symlink target technically tells you which physical port the adapter is plugged into.
If you're not familiar with the convention for USB device numbering (which forms a tree of nodes, since a port can have a USB hub with multiple additional ports, etc), look under /sys/bus/usb/devices, and match that up with the "lsusb" output and you should figure it out. In my case, "lsusb" shows that adapter as "Bus 001 Device 004: ID 0a5c:21e8 Broadcom Corp. BCM20702A0 Bluetooth 4.0", which if I recall corresponds to the "1-3" stuff in the /sys/class/bluetooth path (where unfortunately it appears the bus value uses index origin 1, while the device number uses index origin 0 so the 4 turns into a 3 there).
If you experiment with moving your USB adapter around to different physical ports, you should be able to work out the pattern.
I don't know if this is what you need, but you should find detailed information about the devices attached through the following command:-
hciconfig -a
This will give you enough details to identify the specific devices. You can add this in a shell script and use some string manipulation and conditionals to figure out your devices.
In my case, I have one BT dongle connected, and running hciconfig -a give the following output:-
hci0: Type: BR/EDR Bus: USB
BD Address: 00:16:A4:06:AC:E6 ACL MTU: 310:10 SCO MTU: 64:8
UP RUNNING
RX bytes:670 acl:0 sco:0 events:46 errors:0
TX bytes:2495 acl:0 sco:0 commands:46 errors:0
Features: 0xff 0xff 0xcf 0xfe 0xdb 0xff 0x5b 0x87
Packet type: DM1 DM3 DM5 DH1 DH3 DH5 HV1 HV2 HV3
Link policy: RSWITCH HOLD SNIFF PARK
Link mode: SLAVE ACCEPT
Name: 'youssif'
Class: 0x0c0000
Service Classes: Rendering, Capturing
Device Class: Miscellaneous,
HCI Version: 4.0 (0x6) Revision: 0x22bb
LMP Version: 4.0 (0x6) Subversion: 0x22bb
Manufacturer: Cambridge Silicon Radio (10)
If this is not sufficient, you can use also use a combination of lsusb and hciconfig commands to figure out which device is connected to what port.

BlueZ: How to set up a GATT server from the command line

I would like to know if there is a way to set up a gatt server from the Linux command line. I know that the BlueZ gatttool command allows you to act as a gatt client and interrogate a remote gatt server, however, I do not think that this tool can be used to set up a server.
What I want to achieve is a gatt server, created from the command line, and can be interrogated by any central device (e.g. iOS or Android device) to connect to the GATT server, discover the services and characteristics, and manipulate the data in the characteristics.
Example:
Gatt Server with 1 service which contains 3 characteristics.
Service uuid = 0xFFFF
Char 1 uuid = 0xAAAA, value = 01, properties = readable
Char 2 uuid = 0xBBBB, value = 00, properties = readable & writable
Char 3 uuid = 0xCCCC, value = 02, properties = notifiable
I am using kernel version 3.11.0 and BlueZ 5.19
So this is now handled with the new bluetoothctl tool. A gatt table can be set up using this tool as follows:-
#bluetoothctl
[bluetoothctl] menu gatt
[bluetoothctl] register-service 0xFFFF # (Choose yes when asked if primary service)
[bluetoothctl] register-characteristic 0xAAAA read # (Select a value of 1 when prompted)
[bluetoothctl] register-characteristic 0xBBBB read,write # (Select a value of 0 when prompted)
[bluetoothctl] register-characteristic 0xCCCC read # (Select a value of 2 when prompted)
[bluetoothctl] register-application # (This commits the services/characteristics and registers the profile)
[bluetoothctl] back
[bluetoothctl] advertise on
I've tried this with a few service/characteristic combinations and was able to get it to work. The GAP (0x1800) and GATT (0x1801) services are available by default and will be part of the GATT table when you advertise. You can also use the following command to see the available services:-
[bluetoothctl] show
Controller 00:AA:BB:CC:DD:EE (public)
Name: MyMachine
Alias: MyMachine
Class: 0x000c0000
Powered: yes
Discoverable: no
Pairable: yes
UUID: Headset AG (00001112-0000-1000-8000-00805f9b34fb)
UUID: Generic Attribute Profile (00001801-0000-1000-8000-00805f9b34fb)
UUID: A/V Remote Control (0000110e-0000-1000-8000-00805f9b34fb)
UUID: Generic Access Profile (00001800-0000-1000-8000-00805f9b34fb)
UUID: PnP Information (00001200-0000-1000-8000-00805f9b34fb)
UUID: A/V Remote Control Target (0000110c-0000-1000-8000-00805f9b34fb)
UUID: Audio Source (0000110a-0000-1000-8000-00805f9b34fb)
UUID: Audio Sink (0000110b-0000-1000-8000-00805f9b34fb)
**UUID: Unknown (0000ffff-0000-1000-8000-00805f9b34fb)**
UUID: Headset (00001108-0000-1000-8000-00805f9b34fb)
Modalias: usb:v1D6Bp0246d0532
Discovering: no
I have also faced the same issue, but could find any proper solution, what you can best do using a bluez stack on an Ubuntu machine is use some hci commands to advertise LE packets. These packets will be constantly advertised as the this is if it is an LE server, If you go for scan using an GATT Client you will get the name of your bluez device on the scan list.
Use the following commands below:
Set the LE advertisement packets by the following command:
sudo hcitool -i hcix cmd 0x08 0x0008 1E 02 01 1A 1A FF 4C 00 02 15 E2 0A 39 F4 73 F5 4B C4 A1 2F 17 D1 AD 07 A9 61 00 00 00 00 C8 00
ยท Now advertise the LE packets by the following command:
sudo hciconfig hcix leadv
I believe it is not possible to setup GattServer from CLI.
Mainly because it is a upper layer functionality so there is no tool available to do it (as most of the tools provide lower layer functionalities).
But you can use mimic the way bluez creates service using dbus.
We needed a GattService with two characteristics (R,W,N)
What we ended up doing was following -
1. use the libgdbus (from bluez source) It has all the dbus wrapper to register services to bluez.
Created a translator (socket IPC) to separate the licensing issue (GPL)
Send command to the service registrar to create a service
e,g - op_code = create_service, uuid = 'service_uuid'
op_code = create_charac, uuid='charac_uuid' flags='rwn'
Hope this helps.

change Bluetooth from master to slave using bluez library

Description:
I have a small in-house device with bluetooth capabilities.
At the moment , other devices connect to that box.
Requirement:
Now we have to make it slave so that it get connected with other devices. I am wondering how to do it ? I don't need source code or anything just your views.
Additional Information:
The application uses Bluez libraires to send command to firmware/hardware and we extensively use HCItool.
Operating system :
Fedora.
I am also wondering , do I need to change chipset? From google it doesnt look like we need to change it.
Any help will be beneficial to us.
Thanks
From the command line, the way to achieve what you want is to use the #hcitool. However, you must first be connected. Try this sequence:
hcitool cc AA:BB:CC:DD:EE:FF #Connect to the device
hcitool con #To make sure you are in a connection
hcitool sr AA:BB:CC:DD:EE:FF <role> #switch master/slave role
If the output of "hcitool con" indicates that you are not in a connection, try the following sequence:
hciconfig hci0 sspmode 1
hciconfig hci0 piscan
sdptool add SP
rfcomm connect /dev/rfcomm0 AA:BB:CC:DD:EE:FF 1 &
hcitool con
hcitool sr AA:BB:CC:DD:EE:FF <role>
The above code is specifically for the serial profile, but it has worked for me on several occasions when 'hcitool cc' failed.
If you want to see the source code for this, open the tools/hcitool.c source file in the bluez directory and navigate to the function:
static void cmd_sr(int dev_id, int argc, char **argv)
This is the function that fires up the sequence for switching between master and slave role. Following this function you can see what exactly happens through the bluez stack.
I hope this helps.

Resources