xref: /nrf52832-nimble/packages/NimBLE-latest/apps/blecsc/src/gatt_svr.c (revision 042d53a763ad75cb1465103098bb88c245d95138)
1*042d53a7SEvalZero /*
2*042d53a7SEvalZero  * Licensed to the Apache Software Foundation (ASF) under one
3*042d53a7SEvalZero  * or more contributor license agreements.  See the NOTICE file
4*042d53a7SEvalZero  * distributed with this work for additional information
5*042d53a7SEvalZero  * regarding copyright ownership.  The ASF licenses this file
6*042d53a7SEvalZero  * to you under the Apache License, Version 2.0 (the
7*042d53a7SEvalZero  * "License"); you may not use this file except in compliance
8*042d53a7SEvalZero  * with the License.  You may obtain a copy of the License at
9*042d53a7SEvalZero  *
10*042d53a7SEvalZero  *  http://www.apache.org/licenses/LICENSE-2.0
11*042d53a7SEvalZero  *
12*042d53a7SEvalZero  * Unless required by applicable law or agreed to in writing,
13*042d53a7SEvalZero  * software distributed under the License is distributed on an
14*042d53a7SEvalZero  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15*042d53a7SEvalZero  * KIND, either express or implied.  See the License for the
16*042d53a7SEvalZero  * specific language governing permissions and limitations
17*042d53a7SEvalZero  * under the License.
18*042d53a7SEvalZero  */
19*042d53a7SEvalZero 
20*042d53a7SEvalZero #include <assert.h>
21*042d53a7SEvalZero #include <stdio.h>
22*042d53a7SEvalZero #include <string.h>
23*042d53a7SEvalZero #include <rtthread.h>
24*042d53a7SEvalZero #include "host/ble_hs.h"
25*042d53a7SEvalZero #include "host/ble_uuid.h"
26*042d53a7SEvalZero #include "blecsc_sens.h"
27*042d53a7SEvalZero 
28*042d53a7SEvalZero #define CSC_ERR_CCC_DESC_IMPROPERLY_CONFIGURED  0x81
29*042d53a7SEvalZero 
30*042d53a7SEvalZero static const char *manuf_name = "Apache Mynewt";
31*042d53a7SEvalZero static const char *model_num = "Mynewt CSC Sensor";
32*042d53a7SEvalZero 
33*042d53a7SEvalZero static const uint8_t csc_supported_sensor_locations[] = {
34*042d53a7SEvalZero     SENSOR_LOCATION_FRONT_WHEEL,
35*042d53a7SEvalZero     SENSOR_LOCATION_REAR_DROPOUT,
36*042d53a7SEvalZero     SENSOR_LOCATION_CHAINSTAY,
37*042d53a7SEvalZero     SENSOR_LOCATION_REAR_WHEEL
38*042d53a7SEvalZero };
39*042d53a7SEvalZero 
40*042d53a7SEvalZero static uint8_t sensor_location = SENSOR_LOCATION_REAR_DROPOUT;
41*042d53a7SEvalZero static struct ble_csc_measurement_state * measurement_state;
42*042d53a7SEvalZero uint16_t csc_measurement_handle;
43*042d53a7SEvalZero uint16_t csc_control_point_handle;
44*042d53a7SEvalZero uint8_t csc_cp_indication_status;
45*042d53a7SEvalZero 
46*042d53a7SEvalZero static int
47*042d53a7SEvalZero gatt_svr_chr_access_csc_measurement(uint16_t conn_handle,
48*042d53a7SEvalZero                                     uint16_t attr_handle,
49*042d53a7SEvalZero                                     struct ble_gatt_access_ctxt *ctxt,
50*042d53a7SEvalZero                                     void *arg);
51*042d53a7SEvalZero 
52*042d53a7SEvalZero static int
53*042d53a7SEvalZero gatt_svr_chr_access_csc_feature(uint16_t conn_handle,
54*042d53a7SEvalZero                                 uint16_t attr_handle,
55*042d53a7SEvalZero                                 struct ble_gatt_access_ctxt *ctxt,
56*042d53a7SEvalZero                                 void *arg);
57*042d53a7SEvalZero 
58*042d53a7SEvalZero static int
59*042d53a7SEvalZero gatt_svr_chr_access_sensor_location(uint16_t conn_handle,
60*042d53a7SEvalZero                                     uint16_t attr_handle,
61*042d53a7SEvalZero                                     struct ble_gatt_access_ctxt *ctxt,
62*042d53a7SEvalZero                                     void *arg);
63*042d53a7SEvalZero 
64*042d53a7SEvalZero static int
65*042d53a7SEvalZero gatt_svr_chr_access_sc_control_point(uint16_t conn_handle,
66*042d53a7SEvalZero                                      uint16_t attr_handle,
67*042d53a7SEvalZero                                      struct ble_gatt_access_ctxt *ctxt,
68*042d53a7SEvalZero                                      void *arg);
69*042d53a7SEvalZero 
70*042d53a7SEvalZero static int
71*042d53a7SEvalZero gatt_svr_chr_access_device_info(uint16_t conn_handle,
72*042d53a7SEvalZero                                 uint16_t attr_handle,
73*042d53a7SEvalZero                                 struct ble_gatt_access_ctxt *ctxt,
74*042d53a7SEvalZero                                 void *arg);
75*042d53a7SEvalZero 
76*042d53a7SEvalZero static const struct ble_gatt_svc_def gatt_svr_svcs[] = {
77*042d53a7SEvalZero     {
78*042d53a7SEvalZero         /* Service: Cycling Speed and Cadence */
79*042d53a7SEvalZero         .type = BLE_GATT_SVC_TYPE_PRIMARY,
80*042d53a7SEvalZero         .uuid = BLE_UUID16_DECLARE(GATT_CSC_UUID),
81*042d53a7SEvalZero         .characteristics = (struct ble_gatt_chr_def[]) { {
82*042d53a7SEvalZero             /* Characteristic: Cycling Speed and Cadence Measurement */
83*042d53a7SEvalZero             .uuid = BLE_UUID16_DECLARE(GATT_CSC_MEASUREMENT_UUID),
84*042d53a7SEvalZero             .access_cb = gatt_svr_chr_access_csc_measurement,
85*042d53a7SEvalZero             .val_handle = &csc_measurement_handle,
86*042d53a7SEvalZero             .flags = BLE_GATT_CHR_F_NOTIFY,
87*042d53a7SEvalZero         }, {
88*042d53a7SEvalZero             /* Characteristic: Cycling Speed and Cadence features */
89*042d53a7SEvalZero             .uuid = BLE_UUID16_DECLARE(GATT_CSC_FEATURE_UUID),
90*042d53a7SEvalZero             .access_cb = gatt_svr_chr_access_csc_feature,
91*042d53a7SEvalZero             .flags = BLE_GATT_CHR_F_READ,
92*042d53a7SEvalZero         }, {
93*042d53a7SEvalZero             /* Characteristic: Sensor Location */
94*042d53a7SEvalZero             .uuid = BLE_UUID16_DECLARE(GATT_SENSOR_LOCATION_UUID),
95*042d53a7SEvalZero             .access_cb = gatt_svr_chr_access_sensor_location,
96*042d53a7SEvalZero             .flags = BLE_GATT_CHR_F_READ,
97*042d53a7SEvalZero         }, {
98*042d53a7SEvalZero             /* Characteristic: SC Control Point*/
99*042d53a7SEvalZero             .uuid = BLE_UUID16_DECLARE(GATT_SC_CONTROL_POINT_UUID),
100*042d53a7SEvalZero             .access_cb = gatt_svr_chr_access_sc_control_point,
101*042d53a7SEvalZero             .val_handle = &csc_control_point_handle,
102*042d53a7SEvalZero             .flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_INDICATE,
103*042d53a7SEvalZero         }, {
104*042d53a7SEvalZero             0, /* No more characteristics in this service */
105*042d53a7SEvalZero         }, }
106*042d53a7SEvalZero     },
107*042d53a7SEvalZero 
108*042d53a7SEvalZero     {
109*042d53a7SEvalZero         /* Service: Device Information */
110*042d53a7SEvalZero         .type = BLE_GATT_SVC_TYPE_PRIMARY,
111*042d53a7SEvalZero         .uuid = BLE_UUID16_DECLARE(GATT_DEVICE_INFO_UUID),
112*042d53a7SEvalZero         .characteristics = (struct ble_gatt_chr_def[]) { {
113*042d53a7SEvalZero             /* Characteristic: * Manufacturer name */
114*042d53a7SEvalZero             .uuid = BLE_UUID16_DECLARE(GATT_MANUFACTURER_NAME_UUID),
115*042d53a7SEvalZero             .access_cb = gatt_svr_chr_access_device_info,
116*042d53a7SEvalZero             .flags = BLE_GATT_CHR_F_READ,
117*042d53a7SEvalZero         }, {
118*042d53a7SEvalZero             /* Characteristic: Model number string */
119*042d53a7SEvalZero             .uuid = BLE_UUID16_DECLARE(GATT_MODEL_NUMBER_UUID),
120*042d53a7SEvalZero             .access_cb = gatt_svr_chr_access_device_info,
121*042d53a7SEvalZero             .flags = BLE_GATT_CHR_F_READ,
122*042d53a7SEvalZero         }, {
123*042d53a7SEvalZero             0, /* No more characteristics in this service */
124*042d53a7SEvalZero         }, }
125*042d53a7SEvalZero     },
126*042d53a7SEvalZero 
127*042d53a7SEvalZero     {
128*042d53a7SEvalZero         0, /* No more services */
129*042d53a7SEvalZero     },
130*042d53a7SEvalZero };
131*042d53a7SEvalZero 
132*042d53a7SEvalZero static int
gatt_svr_chr_access_csc_measurement(uint16_t conn_handle,uint16_t attr_handle,struct ble_gatt_access_ctxt * ctxt,void * arg)133*042d53a7SEvalZero gatt_svr_chr_access_csc_measurement(uint16_t conn_handle, uint16_t attr_handle,
134*042d53a7SEvalZero                                   struct ble_gatt_access_ctxt *ctxt, void *arg)
135*042d53a7SEvalZero {
136*042d53a7SEvalZero     return BLE_ATT_ERR_READ_NOT_PERMITTED;
137*042d53a7SEvalZero }
138*042d53a7SEvalZero 
139*042d53a7SEvalZero static int
gatt_svr_chr_access_csc_feature(uint16_t conn_handle,uint16_t attr_handle,struct ble_gatt_access_ctxt * ctxt,void * arg)140*042d53a7SEvalZero gatt_svr_chr_access_csc_feature(uint16_t conn_handle, uint16_t attr_handle,
141*042d53a7SEvalZero                                 struct ble_gatt_access_ctxt *ctxt, void *arg)
142*042d53a7SEvalZero {
143*042d53a7SEvalZero     static const uint16_t csc_feature = CSC_FEATURES;
144*042d53a7SEvalZero     int rc;
145*042d53a7SEvalZero 
146*042d53a7SEvalZero     assert(ctxt->op == BLE_GATT_ACCESS_OP_READ_CHR);
147*042d53a7SEvalZero     rc = os_mbuf_append(ctxt->om, &csc_feature, sizeof(csc_feature));
148*042d53a7SEvalZero 
149*042d53a7SEvalZero     return (rc == 0) ? 0 : BLE_ATT_ERR_INSUFFICIENT_RES;
150*042d53a7SEvalZero }
151*042d53a7SEvalZero 
152*042d53a7SEvalZero static int
gatt_svr_chr_access_sensor_location(uint16_t conn_handle,uint16_t attr_handle,struct ble_gatt_access_ctxt * ctxt,void * arg)153*042d53a7SEvalZero gatt_svr_chr_access_sensor_location(uint16_t conn_handle, uint16_t attr_handle,
154*042d53a7SEvalZero                                   struct ble_gatt_access_ctxt *ctxt, void *arg)
155*042d53a7SEvalZero {
156*042d53a7SEvalZero     int rc;
157*042d53a7SEvalZero 
158*042d53a7SEvalZero     assert(ctxt->op == BLE_GATT_ACCESS_OP_READ_CHR);
159*042d53a7SEvalZero     rc = os_mbuf_append(ctxt->om, &sensor_location, sizeof(sensor_location));
160*042d53a7SEvalZero 
161*042d53a7SEvalZero     return (rc == 0) ? 0 : BLE_ATT_ERR_INSUFFICIENT_RES;
162*042d53a7SEvalZero }
163*042d53a7SEvalZero 
164*042d53a7SEvalZero static int
gatt_svr_chr_access_sc_control_point(uint16_t conn_handle,uint16_t attr_handle,struct ble_gatt_access_ctxt * ctxt,void * arg)165*042d53a7SEvalZero gatt_svr_chr_access_sc_control_point(uint16_t conn_handle,
166*042d53a7SEvalZero                                      uint16_t attr_handle,
167*042d53a7SEvalZero                                      struct ble_gatt_access_ctxt *ctxt,
168*042d53a7SEvalZero                                      void *arg)
169*042d53a7SEvalZero {
170*042d53a7SEvalZero     uint8_t op_code;
171*042d53a7SEvalZero     uint8_t new_sensor_location;
172*042d53a7SEvalZero     uint8_t new_cumulative_wheel_rev_arr[4];
173*042d53a7SEvalZero     struct os_mbuf *om_indication;
174*042d53a7SEvalZero     uint8_t response = SC_CP_RESPONSE_OP_NOT_SUPPORTED;
175*042d53a7SEvalZero     int ii;
176*042d53a7SEvalZero     int rc;
177*042d53a7SEvalZero 
178*042d53a7SEvalZero     assert(ctxt->op == BLE_GATT_ACCESS_OP_WRITE_CHR);
179*042d53a7SEvalZero 
180*042d53a7SEvalZero     if (!csc_cp_indication_status) {
181*042d53a7SEvalZero         MODLOG_DFLT(INFO, "SC Control Point; CCC descriptor "
182*042d53a7SEvalZero                           "improperly configured");
183*042d53a7SEvalZero         return CSC_ERR_CCC_DESC_IMPROPERLY_CONFIGURED;
184*042d53a7SEvalZero     }
185*042d53a7SEvalZero 
186*042d53a7SEvalZero     /* Read control point op code*/
187*042d53a7SEvalZero     rc = os_mbuf_copydata(ctxt->om, 0, sizeof(op_code), &op_code);
188*042d53a7SEvalZero     if (rc != 0){
189*042d53a7SEvalZero         return BLE_ATT_ERR_INVALID_ATTR_VALUE_LEN;
190*042d53a7SEvalZero     }
191*042d53a7SEvalZero     MODLOG_DFLT(INFO, "SC Control Point; opcode=%d\n", op_code);
192*042d53a7SEvalZero 
193*042d53a7SEvalZero     /* Allocate response buffer */
194*042d53a7SEvalZero     om_indication = ble_hs_mbuf_att_pkt();
195*042d53a7SEvalZero 
196*042d53a7SEvalZero     switch(op_code){
197*042d53a7SEvalZero #if (CSC_FEATURES & CSC_FEATURE_WHEEL_REV_DATA)
198*042d53a7SEvalZero     case SC_CP_OP_SET_CUMULATIVE_VALUE:
199*042d53a7SEvalZero         /* Read new cumulative wheel revolutions value*/
200*042d53a7SEvalZero         rc = os_mbuf_copydata(ctxt->om, 1,
201*042d53a7SEvalZero                               sizeof(new_cumulative_wheel_rev_arr),
202*042d53a7SEvalZero                               new_cumulative_wheel_rev_arr);
203*042d53a7SEvalZero         if (rc != 0){
204*042d53a7SEvalZero             return BLE_ATT_ERR_INVALID_ATTR_VALUE_LEN;
205*042d53a7SEvalZero         }
206*042d53a7SEvalZero 
207*042d53a7SEvalZero         measurement_state->cumulative_wheel_rev =
208*042d53a7SEvalZero                            get_le32(new_cumulative_wheel_rev_arr);
209*042d53a7SEvalZero 
210*042d53a7SEvalZero         MODLOG_DFLT(INFO, "SC Control Point; Set cumulative value = %d\n",
211*042d53a7SEvalZero                     measurement_state->cumulative_wheel_rev);
212*042d53a7SEvalZero 
213*042d53a7SEvalZero         response = SC_CP_RESPONSE_SUCCESS;
214*042d53a7SEvalZero         break;
215*042d53a7SEvalZero #endif
216*042d53a7SEvalZero 
217*042d53a7SEvalZero #if (CSC_FEATURES & CSC_FEATURE_MULTIPLE_SENSOR_LOC)
218*042d53a7SEvalZero     case SC_CP_OP_UPDATE_SENSOR_LOCATION:
219*042d53a7SEvalZero         /* Read new sensor location value*/
220*042d53a7SEvalZero         rc = os_mbuf_copydata(ctxt->om, 1, 1, &new_sensor_location);
221*042d53a7SEvalZero         if (rc != 0){
222*042d53a7SEvalZero           return BLE_ATT_ERR_INVALID_ATTR_VALUE_LEN;
223*042d53a7SEvalZero         }
224*042d53a7SEvalZero 
225*042d53a7SEvalZero         MODLOG_DFLT(INFO, "SC Control Point; Sensor location update = %d\n",
226*042d53a7SEvalZero                     new_sensor_location);
227*042d53a7SEvalZero 
228*042d53a7SEvalZero         /* Verify if requested new location is on supported locations list */
229*042d53a7SEvalZero         response = SC_CP_RESPONSE_INVALID_PARAM;
230*042d53a7SEvalZero         for (ii = 0; ii < sizeof(csc_supported_sensor_locations); ii++){
231*042d53a7SEvalZero             if (new_sensor_location == csc_supported_sensor_locations[ii]){
232*042d53a7SEvalZero                 sensor_location = new_sensor_location;
233*042d53a7SEvalZero                 response = SC_CP_RESPONSE_SUCCESS;
234*042d53a7SEvalZero                 break;
235*042d53a7SEvalZero             }
236*042d53a7SEvalZero         }
237*042d53a7SEvalZero         break;
238*042d53a7SEvalZero 
239*042d53a7SEvalZero     case SC_CP_OP_REQ_SUPPORTED_SENSOR_LOCATIONS:
240*042d53a7SEvalZero         response = SC_CP_RESPONSE_SUCCESS;
241*042d53a7SEvalZero         break;
242*042d53a7SEvalZero #endif
243*042d53a7SEvalZero 
244*042d53a7SEvalZero     default:
245*042d53a7SEvalZero         break;
246*042d53a7SEvalZero     }
247*042d53a7SEvalZero 
248*042d53a7SEvalZero     /* Append response value */
249*042d53a7SEvalZero     rc = os_mbuf_append(om_indication, &response, sizeof(response));
250*042d53a7SEvalZero 
251*042d53a7SEvalZero     if (rc != 0){
252*042d53a7SEvalZero       return BLE_ATT_ERR_INSUFFICIENT_RES;
253*042d53a7SEvalZero     }
254*042d53a7SEvalZero 
255*042d53a7SEvalZero #if (CSC_FEATURES & CSC_FEATURE_MULTIPLE_SENSOR_LOC)
256*042d53a7SEvalZero     /* In case of supported locations request append locations list */
257*042d53a7SEvalZero     if (op_code == SC_CP_OP_REQ_SUPPORTED_SENSOR_LOCATIONS){
258*042d53a7SEvalZero       rc = os_mbuf_append(om_indication, &csc_supported_sensor_locations,
259*042d53a7SEvalZero                           sizeof(csc_supported_sensor_locations));
260*042d53a7SEvalZero     }
261*042d53a7SEvalZero 
262*042d53a7SEvalZero     if (rc != 0){
263*042d53a7SEvalZero       return BLE_ATT_ERR_INSUFFICIENT_RES;
264*042d53a7SEvalZero     }
265*042d53a7SEvalZero #endif
266*042d53a7SEvalZero 
267*042d53a7SEvalZero     rc = ble_gattc_indicate_custom(conn_handle, csc_control_point_handle,
268*042d53a7SEvalZero                                    om_indication);
269*042d53a7SEvalZero 
270*042d53a7SEvalZero     return rc;
271*042d53a7SEvalZero }
272*042d53a7SEvalZero 
273*042d53a7SEvalZero static int
gatt_svr_chr_access_device_info(uint16_t conn_handle,uint16_t attr_handle,struct ble_gatt_access_ctxt * ctxt,void * arg)274*042d53a7SEvalZero gatt_svr_chr_access_device_info(uint16_t conn_handle, uint16_t attr_handle,
275*042d53a7SEvalZero                                 struct ble_gatt_access_ctxt *ctxt, void *arg)
276*042d53a7SEvalZero {
277*042d53a7SEvalZero     uint16_t uuid;
278*042d53a7SEvalZero     int rc;
279*042d53a7SEvalZero 
280*042d53a7SEvalZero     uuid = ble_uuid_u16(ctxt->chr->uuid);
281*042d53a7SEvalZero 
282*042d53a7SEvalZero     if (uuid == GATT_MODEL_NUMBER_UUID) {
283*042d53a7SEvalZero         rc = os_mbuf_append(ctxt->om, model_num, strlen(model_num));
284*042d53a7SEvalZero         return rc == 0 ? 0 : BLE_ATT_ERR_INSUFFICIENT_RES;
285*042d53a7SEvalZero     }
286*042d53a7SEvalZero 
287*042d53a7SEvalZero     if (uuid == GATT_MANUFACTURER_NAME_UUID) {
288*042d53a7SEvalZero         rc = os_mbuf_append(ctxt->om, manuf_name, strlen(manuf_name));
289*042d53a7SEvalZero         return rc == 0 ? 0 : BLE_ATT_ERR_INSUFFICIENT_RES;
290*042d53a7SEvalZero     }
291*042d53a7SEvalZero 
292*042d53a7SEvalZero     assert(0);
293*042d53a7SEvalZero     return BLE_ATT_ERR_UNLIKELY;
294*042d53a7SEvalZero }
295*042d53a7SEvalZero 
296*042d53a7SEvalZero int
gatt_svr_chr_notify_csc_measurement(uint16_t conn_handle)297*042d53a7SEvalZero gatt_svr_chr_notify_csc_measurement(uint16_t conn_handle)
298*042d53a7SEvalZero {
299*042d53a7SEvalZero     int rc;
300*042d53a7SEvalZero     struct os_mbuf *om;
301*042d53a7SEvalZero     uint8_t data_buf[11];
302*042d53a7SEvalZero     uint8_t data_offset = 1;
303*042d53a7SEvalZero 
304*042d53a7SEvalZero     memset(data_buf, 0, sizeof(data_buf));
305*042d53a7SEvalZero 
306*042d53a7SEvalZero #if (CSC_FEATURES & CSC_FEATURE_WHEEL_REV_DATA)
307*042d53a7SEvalZero     data_buf[0] |= CSC_MEASUREMENT_WHEEL_REV_PRESENT;
308*042d53a7SEvalZero     put_le16(&(data_buf[5]), measurement_state->last_wheel_evt_time);
309*042d53a7SEvalZero     put_le32(&(data_buf[1]), measurement_state->cumulative_wheel_rev);
310*042d53a7SEvalZero     data_offset += 6;
311*042d53a7SEvalZero #endif
312*042d53a7SEvalZero 
313*042d53a7SEvalZero #if (CSC_FEATURES & CSC_FEATURE_CRANK_REV_DATA)
314*042d53a7SEvalZero     data_buf[0] |= CSC_MEASUREMENT_CRANK_REV_PRESENT;
315*042d53a7SEvalZero     put_le16(&(data_buf[data_offset]),
316*042d53a7SEvalZero              measurement_state->cumulative_crank_rev);
317*042d53a7SEvalZero     put_le16(&(data_buf[data_offset + 2]),
318*042d53a7SEvalZero              measurement_state->last_crank_evt_time);
319*042d53a7SEvalZero     data_offset += 4;
320*042d53a7SEvalZero #endif
321*042d53a7SEvalZero 
322*042d53a7SEvalZero     om = ble_hs_mbuf_from_flat(data_buf, data_offset);
323*042d53a7SEvalZero 
324*042d53a7SEvalZero     rc = ble_gattc_notify_custom(conn_handle, csc_measurement_handle, om);
325*042d53a7SEvalZero     return rc;
326*042d53a7SEvalZero }
327*042d53a7SEvalZero 
328*042d53a7SEvalZero void
gatt_svr_set_cp_indicate(uint8_t indication_status)329*042d53a7SEvalZero gatt_svr_set_cp_indicate(uint8_t indication_status)
330*042d53a7SEvalZero {
331*042d53a7SEvalZero   csc_cp_indication_status = indication_status;
332*042d53a7SEvalZero }
333*042d53a7SEvalZero 
334*042d53a7SEvalZero void
gatt_svr_register_cb(struct ble_gatt_register_ctxt * ctxt,void * arg)335*042d53a7SEvalZero gatt_svr_register_cb(struct ble_gatt_register_ctxt *ctxt, void *arg)
336*042d53a7SEvalZero {
337*042d53a7SEvalZero     char buf[BLE_UUID_STR_LEN];
338*042d53a7SEvalZero 
339*042d53a7SEvalZero     switch (ctxt->op) {
340*042d53a7SEvalZero     case BLE_GATT_REGISTER_OP_SVC:
341*042d53a7SEvalZero         MODLOG_DFLT(DEBUG, "registered service %s with handle=%d\n",
342*042d53a7SEvalZero                     ble_uuid_to_str(ctxt->svc.svc_def->uuid, buf),
343*042d53a7SEvalZero                     ctxt->svc.handle);
344*042d53a7SEvalZero         break;
345*042d53a7SEvalZero 
346*042d53a7SEvalZero     case BLE_GATT_REGISTER_OP_CHR:
347*042d53a7SEvalZero         MODLOG_DFLT(DEBUG, "registering characteristic %s with "
348*042d53a7SEvalZero                            "def_handle=%d val_handle=%d\n",
349*042d53a7SEvalZero                     ble_uuid_to_str(ctxt->chr.chr_def->uuid, buf),
350*042d53a7SEvalZero                     ctxt->chr.def_handle,
351*042d53a7SEvalZero                     ctxt->chr.val_handle);
352*042d53a7SEvalZero         break;
353*042d53a7SEvalZero 
354*042d53a7SEvalZero     case BLE_GATT_REGISTER_OP_DSC:
355*042d53a7SEvalZero         MODLOG_DFLT(DEBUG, "registering descriptor %s with handle=%d\n",
356*042d53a7SEvalZero                     ble_uuid_to_str(ctxt->dsc.dsc_def->uuid, buf),
357*042d53a7SEvalZero                     ctxt->dsc.handle);
358*042d53a7SEvalZero         break;
359*042d53a7SEvalZero 
360*042d53a7SEvalZero     default:
361*042d53a7SEvalZero         assert(0);
362*042d53a7SEvalZero         break;
363*042d53a7SEvalZero     }
364*042d53a7SEvalZero }
365*042d53a7SEvalZero 
366*042d53a7SEvalZero int
gatt_svr_init(struct ble_csc_measurement_state * csc_measurement_state)367*042d53a7SEvalZero gatt_svr_init(struct ble_csc_measurement_state * csc_measurement_state)
368*042d53a7SEvalZero {
369*042d53a7SEvalZero     int rc;
370*042d53a7SEvalZero 
371*042d53a7SEvalZero     rc = ble_gatts_count_cfg(gatt_svr_svcs);
372*042d53a7SEvalZero     if (rc != 0) {
373*042d53a7SEvalZero         return rc;
374*042d53a7SEvalZero     }
375*042d53a7SEvalZero 
376*042d53a7SEvalZero     rc = ble_gatts_add_svcs(gatt_svr_svcs);
377*042d53a7SEvalZero     if (rc != 0) {
378*042d53a7SEvalZero         return rc;
379*042d53a7SEvalZero     }
380*042d53a7SEvalZero 
381*042d53a7SEvalZero     measurement_state = csc_measurement_state;
382*042d53a7SEvalZero 
383*042d53a7SEvalZero     return 0;
384*042d53a7SEvalZero }
385