component/bt: Modify docs to be compatible with "Github Standard Markdown"

This commit is contained in:
island
2018-01-03 11:07:55 +08:00
parent 85efc08c27
commit 5c82ef1034
5 changed files with 127 additions and 96 deletions
@@ -1,8 +1,11 @@
# GATT SERVER EXAMPLE WALKTHROUGH
##INTRODUCTION
# Gatt Server Example Walkthrough
## Introduction
In this document, we review the GATT SERVER example code which implements a Bluetooth Low Energy (BLE) Generic Attribute Profile (GATT) Server on the ESP32. This example is designed around two Application Profiles and a series of events that are handled in order to execute a sequence of configuration steps, such as defining advertising parameters, updating connection parameters and creating services and characteristics. In addition, this example handles read and write events, including a Write Long Characteristic request, which divides the incoming data into chunks so that the data can fit in the Attribute Protocol (ATT) message. This document follows the program workflow and breaks down the code in order to make sense of every section and reasoning behind the implementation.
#INCLUDES
## Includes
First, lets take a look at the includes:
```c
@@ -30,7 +33,8 @@ These includes are required for the FreeRTOS and underlaying system components t
* `esp_gap_ble_api.h`: implements GAP configuration, such as advertising and connection parameters.
* `esp_gatts_api.h`: implements GATT configuration, such as creating services and characteristics.
## MAIN ENTRY POINT
## Main Entry Point
The entry point to this example is the app_main() function:
```c
@@ -101,7 +105,8 @@ The main function starts by initializing the non-volatile storage library. This
```c
ret = nvs_flash_init();
```
##BT CONTROLLER AND STACK INITIALIZATION
## BT Controller and Stack Initialization
The main function also initializes the BT controller by first creating a BT controller configuration structure named `esp_bt_controller_config_t` with default settings generated by the `BT_CONTROLLER_INIT_CONFIG_DEFAULT()` macro. The BT controller implements the Host Controller Interface (HCI) on the controller side, the Link Layer (LL) and the Physical Layer (PHY). The BT Controller is invisible to the user applications and deals with the lower layers of the BLE stack. The controller configuration includes setting the BT controller stack size, priority and HCI baud rate. With the settings created, the BT controller is initialized and enabled with the `esp_bt_controller_init()` function:
```c
@@ -135,13 +140,13 @@ esp_ble_gap_register_callback(gap_event_handler);
```
The functions `gatts_event_handler()` and `gap_event_handler()` handle all the events that are pushed to the application from the BLE stack.
##APPLICATION PROFILES
## APPLICATION PROFILES
The GATT Server example application is organized by using Application Profiles as shown in Fig 1. Each Application Profile describes a way to group functionalities that are designed for one client application, such as a mobile app running on a smartphone or tablet. In this way, a single design, enabled by different Application Profiles, can behave differently when used by different smartphone apps, allowing the server to react differently according to the client app that is being used. In practice, each profile is seen by the client as an independent BLE service. It is up to the client to discriminate the services that it is interested in.
![](image/GATT SERVER FIGURE 1.png)
<p align="center">Fig.1. Application Profiles are used to organize a BLE application in order to implement different functionality for different clients.</p>
Each profile is defined as a struct where the struct members depend on the services and characteristics that are implemented in that Application Profile. The members also include a GATT interface, Application ID, Connection ID and a callback function to handle profile events. In this example, each profile is composed by:
* GATT interface
@@ -196,7 +201,8 @@ esp_ble_gatts_app_register(PROFILE_A_APP_ID);
esp_ble_gatts_app_register(PROFILE_B_APP_ID);
```
##SETTING GAP PARAMETERS
## Setting GAP Parameters
The register application event is the first one that is triggered during the lifetime of the program, this example uses the Profile A GATT event handle to configure the advertising parameters upon registration. This example has the option to use both standard Bluetooth Core Specification advertising parameters or a customized raw buffer. The option can be selected with the `CONFIG_SET_RAW_ADV_DATA` define. The raw advertising data can be used to implement iBeacons, Eddystone or other proprietaries, and custom frame types such as the ones used for Indoor Location Services that are different from the standard specifications.
The function used to configure standard Bluetooth Specification advertisement parameters is `esp_ble_gap_config_adv_data()`, which takes a pointer to an `esp_ble_adv_data_t` structure. The `esp_ble_adv_data_t` data structure for advertising data has the following definition:
@@ -283,7 +289,8 @@ static void gatts_profile_a_event_handler(esp_gatts_cb_event_t event, esp_gatt_i
adv_config_done |= scan_rsp_config_flag;
#endif
```
##GAP EVENT HANDLER
## GAP Event Handler
Once the advertising data have been set, the GAP event `ESP_GAP_BLE_ADV_DATA_SET_COMPLETE_EVT` is triggered. For the case of raw advertising data set, the event triggered is `ESP_GAP_BLE_ADV_DATA_RAW_SET_COMPLETE_EVT`. Additionally when the raw scan response data is set, `ESP_GAP_BLE_SCAN_RSP_DATA_RAW_SET_COMPLETE_EVT` event is triggered.
```c
@@ -379,7 +386,8 @@ If the advertising started successfully, an `ESP_GAP_BLE_ADV_START_COMPLETE_EVT`
```
##GATT EVENT HANDLERS
## GATT Event Handlers
When an Application Profile is registered, an `ESP_GATTS_REG_EVT` event is triggered. The parameters of the `ESP_GATTS_REG_EVT` are:
* `esp_gatt_status_t status; /*!< Operation status */`
@@ -417,7 +425,8 @@ static void gatts_event_handler(esp_gatts_cb_event_t event, esp_gatt_if_t gatts_
}
```
##CREATING SERVICES
## Creating Services
The register event is also used to create a profile attributes table by using the `esp_ble_gatts_create_attr_tab()` function, which takes an `esp_gatts_attr_db_t` type structure that has all the information of the service table. The way to create this table is:
```c
@@ -461,7 +470,8 @@ static void gatts_profile_b_event_handler(esp_gatts_cb_event_t event, esp_gatt_i
}
```
##STARTING SERVICES AND CREATING CHARACTERISTICS
## Starting Services and Creating Characteristics
When a service is created successfully, an `ESP_GATTS_CREATE_EVT` event managed by the profile GATT handler is triggered, and can be used to start the service and add characteristics to the service. For the case of Profile A, the service is started and the characteristics are added as follows:
```c
@@ -527,7 +537,7 @@ The characteristic initial value must be a non-null object and the characteristi
Finally, the characteristic is configured in a way that it is required to send a response manually every time the characteristic is read or written, instead of letting the stack auto respond. This is configured by setting the last parameter of the `esp_ble_gatts_add_char()` function, representing the attribute response control parameter, to `ESP_GATT_RSP_BY_APP` or NULL.
##CREATING THE CHARACTERISTIC DESCRIPTOR
## Creating the Characteristic Descriptor
Adding a characteristic to a service triggers an `ESP_GATTS_ADD_CHAR_EVT` event, which returns the handle generated by the stack for the characteristic just added. The event includes the following parameters:
@@ -579,7 +589,8 @@ Once the descriptor is added, the `ESP_GATTS_ADD_CHAR_DESCR_EVT` event is trigge
```
This procedure is repeated in the Profile B event handler, in order to create the services and characteristics for that profile.
##CONNECTION EVENT
## Connection Event
An `ESP_GATTS_CONNECT_EVT` is triggered when a client has connected to the GATT server. This event is used to update the connection parameters, such as latency, minimum connection interval, maximum connection interval and time out. The connection parameters are stored into an `esp_ble_conn_update_params_t` structure, and then passed to the `esp_ble_gap_update_conn_params()` function. The update connection parameters procedure needs to be done only once, therefore the Profile B connection event handler does not include the `esp_ble_gap_update_conn_params()` function. Finally, the connection ID returned by the event is stored in the profile table.
Profile A connection event:
@@ -641,7 +652,7 @@ The `esp_ble_gap_update_conn_params()` function triggers a GAP event `ESP_GAP_BL
break;
```
##MANAGING READ EVENTS
## Managing Read Events
Now that the services and characteristics are created and started, the program can receive read and write events. The read operations are represented by the `ESP_GATTS_READ_EVT` event, which has the following parameters:
@@ -675,7 +686,8 @@ case ESP_GATTS_READ_EVT: {
}
```
##MANAGING WRITE EVENTS
## Managing Write Events
The write events are represented by the `ESP_GATTS_WRITE_EVT` event, which has the following parameters:
* `uint16_t conn_id;     /*!< Connection id */`
@@ -815,6 +827,7 @@ if (param->write.is_prep){
}
```
To handle long characteristic write, a prepare buffer structure is defined and instantiated:
```c
@@ -906,6 +919,7 @@ void example_exec_write_event_env(prepare_type_env_t *prepare_write_env, esp_ble
prepare_write_env->prepare_len = 0;
}
```
The executive write is used to either confirm or cancel the write procedure done before, by the Long Characteristic Write procedure. In order to do this, the function checks for the `exec_write_flag` in the parameters received with the event. If the flag equals the execute flag represented by `exec_write_flag`, the write is confirmed and the buffer is printed in the log; if not, then it means the write is canceled and all the data that has been written is deleted.
```c
@@ -928,7 +942,7 @@ if (prepare_write_env->prepare_buf) {
prepare_write_env->prepare_len = 0;
```
##CONCLUSION
## Conclusion
In this document, we have gone through the GATT SERVER example code describing each section. The application is designed around the concept of Application Profiles. In addition, the procedures that this example uses to register event handlers are explained. The events follow a sequence of configuration steps, such as defining advertising parameters, updating connection parameters and creating services and characteristics. Finally, the way in which read and write events are handled, including Write Long characteristics by dividing the write into chunks that can fit the Attribute Protocol message is explained.