# Custom Bluetooth Services - A Dialog Custom Implementation

## Example description

This application demonstrates a sophisticated way in creating custom Bluetooth Services. The core mechanism of the application is responsible for creating, initializing and registering custom Bluetooth Services in Dialog attribute database. On top of that mechanism, a friendly abstraction layer has been implemented hiding all the complexity of Bluetooth Services declaration and offering a set of macros that should be used by the developer to build his own custom Bluetooth Services, easily and quickly.



## HW & SW Configurations

- **Hardware Configurations**
    - This example runs on a DA1468x Bluetooth Smart SoC.
    - A DA1468x Basic or Pro or USB Development Kit is needed for this example.
- **Software Configurations**
    - Download the latest SDK version for the DA1468x family of devices, currently version 1.0.14.
    - **SEGGER's J-Link** tools should be downloaded and installed.



## How to run the example

### Initial Setup

- Download the source code from the Support Website.
- Import the project into your workspace.
- Connect the target device to your host PC.
- Modify the source code as needed:



For demonstration purposes the project exhibits two custom Bluetooth Services. The first Bluetooth Service employs an initialized Characteristic Attribute, whilst the second Bluetooth Service includes three uninitialized Characteristic Attributes that can be configured as needed. The user is free to add as many Characteristic Attributes and Bluetooth Services as needed. The only limitation is the available memory space of the target device that should accommodate all the resources of the declared Bluetooth Services.



In `ble_custom_service_task.c` file, use the `MAX_CHAR_ATTR_VAL` macro to define the maximum allowable length of the initialized Characteristic Attribute (expressed in bytes). Please note that the remote device cannot exceed this value when writing the Characteristic Attribute value.



```c
#define MAX_CHAR_ATTR_VAL       (50)
```


Optionally, use the `DBG_SERIAL_CONSOLE` macro to enable debugging messages on the serial console (enabled by default).



```c
#define DBG_SERIAL_CONSOLE      (1)
````


Optionally, use the `MCS_CHANGE_MTU_SIZE_EN` macro to change the default MTU size which is 65 Octets (disabled by default)



```c
#define MCS_CHANGE_MTU_SIZE_EN  (0)
```


- Compile the code and load it into the chip.
- Open a serial terminal (115200/8 - N - 1)
- Press the reset button on DevKit to start executing the application.
- When the project starts running, the DA1468x module should be visible by     
  any Bluetooth scanner application.



Verify the Bluetooth advertising data and the public address:


![Advertising data](assets/ble_adv_data.png)



Press **Connect**, to connect to the peripheral device. The two custom Bluetooth Services should be displayed, along with
the `Generic Access` and `Generic Attribute` Services (the last one is mandatory for all the Bluetooth devices and it is
created automatically by the Bluetooth stack):


![BLE Services](assets/ble_services.png)



Explore the second Bluetooth Service and verify that contains three uninitialized Characteristic Attributes:


![Unitialized BLE Service](assets/ble_service_uninitialized.png)



Explore the first Bluetooth Service and verify that contains one initialized Characteristic Attributes. You can
verify the 128-bit UUIDs as well as the descriptors. Depending on the permission settings, the scanner App will draw the corresponding symbols. For instance, **R** for reading the Characteristic Attribute value, **W** for writing, and **N** or **I** for enabling/disabling notifications/indications respectively:


![Ininitialized BLE Service](assets/ble_service_initialized.png)



To start interacting with the peripheral device, press  **W** and in the pop-up window text a message. (e.g. Hello Word!) The written value and its size should be displayed on the serial console:


![Update Characteristic Value](assets/update_characteristic_value.PNG)


Verify the correct behavior of the Characteristic Attribute by pressing **R**. The current Characteristic Attribute value should be displayed on the serial console (this should be the last written value):


![Read Characteristic Value](assets/read_characteristic_value.PNG)



Press **I** to enable indications and try to write a new value as described previously (e.g. Hello!). The serial console should display two messages. The first one is the written value and the second one is the status of the notification event,
sent by the peripheral device to the remote users.



![notifications](assets/notifications.PNG)



**Note:** The application will automatically send a notification to all the connected peer devices when a Characteristic Attribute value is updated.



**Note:** You should expect to get as many notification callbacks as the number of the connected peer devices. The only
prerequisite is for the remote device to have its notifications enabled.



**Note:** According to Bluetooth core specifications, when the peer device attempts to sent to the peripheral device more than 20 bytes, then the `Prepare Write Request` Bluetooth event is invoked and the written value is split into chunks of 20 bytes which are sent one by one. When all the data packets are received, the peripheral device will concatenate them and provide the data as a unified message. However, some scanner Apps may split the written value into chunks of 20 bytes and send them using separate write requests (without invoking a Prepare Write Request event). If this is the case, you should expect to get the following output on the serial console:

![Split Written Value](assets/split_written_value.png)



**Note:** The `CHARACTERISTIC_DECLARATION()` macro should be declared within an array of type `mcs_characteristic_config_t`:

```c
        const mcs_characteristic_config_t my_service_2[] = {
               CHARACTERISTIC_DECLARATION(...),

               CHARACTERISTIC_DECLARATION(...),

               CHARACTERISTIC_DECLARATION(...),
       };
```



## Known Limitations
There are no known limitations for this application.




## License
**************************************************************************************

 Copyright (c) 2018 Dialog Semiconductor. All rights reserved.

 This software ("Software") is owned by Dialog Semiconductor. By using this Software
 you agree that Dialog Semiconductor retains all intellectual property and proprietary
 rights in and to this Software and any use, reproduction, disclosure or distribution
 of the Software without express written permission or a license agreement from Dialog
 Semiconductor is strictly prohibited. This Software is solely for use on or in
 conjunction with Dialog Semiconductor products.

 EXCEPT AS OTHERWISE PROVIDED IN A LICENSE AGREEMENT BETWEEN THE PARTIES OR AS
 REQUIRED BY LAW, THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
 EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. EXCEPT AS OTHERWISE PROVIDED
 IN A LICENSE AGREEMENT BETWEEN THE PARTIES OR BY LAW, IN NO EVENT SHALL DIALOG
 SEMICONDUCTOR BE LIABLE FOR ANY DIRECT, SPECIAL, INDIRECT, INCIDENTAL, OR
 CONSEQUENTIAL DAMAGES, OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
 PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
 ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THE SOFTWARE.

**************************************************************************************
