How to implement Bluetooth LE with Bluez in Linux

17,787

To create a GATT server into a separate process you have (at least) two cases:

  • Bluez v4.x: your GATT service must be a Bluez plugin
  • Bluez v5.x: your GATT service should use the new GATT DBus API (but it is recommended to use at least Bluez v5.39 (from April 2016). Otherwise it is safer (in term of Bluez GATT Server API) to use the Bluez v4.x plugin approach.

If your Central Device does not see the newly exported GATT service is probably an issue on the periphal rather than to be an issue on the Central Device. When you will need to implement the GATT client on the Central Device you still have two cases:

  • Bluez v4.x: Bluez does not expose the GATT API. Either you use a shell script to launch gatttool commands, or you use a GATT library such as gattlib to interact with the BLE device
  • Bluez v5.x: Same thing, if you cannot migrate to Bluez v5.39 then it is better to use Bluez v4.x methodology.
Share:
17,787

Related videos on Youtube

linsek
Author by

linsek

Updated on April 21, 2020

Comments

  • linsek
    linsek about 4 years

    I'm working on setting up two Linux systems for a BLE demo. Obviously one system will be the peripheral and one will be the central devices. I have several questions surrounding both of these configurations.

    Environment

    Peripheral Device Setup

    The first order of business is getting the peripheral system setup and advertising with a GATT server configured. At this time, it does not seem possible to configure a GATT server from the command line. So, while it is a simple task bringing a USB dongle up and advertising it, this does not allow the creation of custom services and characteristics. The only example of a GATT server I could find was the gatt-example.c file in the Bluez package. So I downloaded and built the latest bluez-5.23 source. (http://www.linuxfromscratch.org/blfs/view/svn/general/bluez.html). Additionally configured using the --enable-maintainer-mode flag to force build the gatt-example.c plugin into bluetoothd. And I validated post-build from the ~/bluez-5.23/plugins directory that there was a bluetoothd-gat-example.o file. Which tells me that the gatt-example was at least successfully built.

    I then modified the configuration file to enable LE and the attribute server.

    $ sudo vi /etc/bluetooth/main.conf
    EnableLE = true           // Enable Low Energy support. Default is false.
    AttributeServer = true    // Enable the GATT attribute server. Default is false.
    

    Then simply reboot or restart the bluetooth daemon...

    Central Device Setup

    As the central device does not need any special plugins built like the peripheral, I just installed bluez using apt-get. This appears to have installed v4.101 according to bluetoothd -v.

    Session Setup

    The connection process then should be fairly simple. I setup the peripheral to advertise and then connect with the central device:

    Peripheral:

    $ sudo hciconfig hci0 up        // Make sure the interface is up
    $ sudo hciconfig hci0 leadv     // Set the interface to advertise
    

    Central:

    $ sudo hcitool -i hci0 lescan   // Scan for nearby devices advertising
    LE Scan ...
    00:02:72:C9:5E:0F (unknown)     // Not sure why two of the same MAC are found?
    00:02:72:C9:5E:0F (unknown)     // but I know this is my device...
    
    $ sudo gatttool -i hci0 -b 00:02:72:C9:5E:0F -m 48 --interactive     // Connect interactively
    [   ][00:02:72:C9:5E:0F][LE]> connect
    [CON][00:02:72:C9:5E:0F][LE]> primary
    attr handle: 0x0001, end grp handle: 0x0008 uuid: 00001800-0000-1000-8000-00805f9b34fb
    attr handle: 0x0010, end grp handle: 0x0010 uuid: 00001801-0000-1000-8000-00805f9b34fb
    [CON][00:02:72:C9:5E:0F][LE]> characteristics 
    handle: 0x0004, char properties: 0x02, char value handle: 0x0006, uuid: 00002a00-0000-1000-8000-00805f9b34fb
    handle: 0x0007, char properties: 0x02, char value handle: 0x0008, uuid: 00002a01-0000-1000-8000-00805f9b34fb
    

    And we see not one of the services or characteristics from the gatt-example are available.

    Questions

    --Peripheral Device

    1. How would I go about creating my own custom GATT server? Can it be a stand-alone C application or does it need to be built into bluetoothd as a plugin like the gatt-example? The answer to this question (Creating a Gatt Server?) implies you do the following: "start by initializing the GATT library and additional modules" and then "register your GATT database". But there isn't a single example of how to implement those generic statements and the link provided is simply a URL to the Bluetooth website.
    2. The GATT specifications (https://developer.bluetooth.org/gatt/Pages/default.aspx) provide numerous "adopted" services and characteristics that are downloadable in XML format. But there is no instructions for how to use them?!
    3. How do a validate my GATT server is running?

    --Central Device

    1. Why is my central device not seeing the services and characteristics from the GATT server running on the peripheral?

    I can provide any additional information necessary. Thanks.

    • jfhc
      jfhc over 9 years
      Rather than using BlueZ directly you might want to consider using a higher level library like Noble and Bleno
    • Zimano
      Zimano over 8 years
      @jfhc There's really no need for that, as BlueZ implements two API's for its functionality, one of which is very high level (DBus)