xref: /nrf52832-nimble/packages/NimBLE-latest/nimble/host/services/dis/src/ble_svc_dis.c (revision 042d53a763ad75cb1465103098bb88c245d95138)
1 /**
2  * Licensed to the Apache Software Foundation (ASF) under one
3  * or more contributor license agreements.  See the NOTICE file
4  * distributed with this work for additional information
5  * regarding copyright ownership.  The ASF licenses this file
6  * to you under the Apache License, Version 2.0 (the
7  * "License"); you may not use this file except in compliance
8  * with the License.  You may obtain a copy of the License at
9  *
10  *  http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing,
13  * software distributed under the License is distributed on an
14  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15  * KIND, either express or implied.  See the License for the
16  * specific language governing permissions and limitations
17  * under the License.
18  */
19 
20 #include <assert.h>
21 #include <string.h>
22 #include "sysinit/sysinit.h"
23 #include "host/ble_hs.h"
24 #include "services/dis/ble_svc_dis.h"
25 
26 /* Device information */
27 struct ble_svc_dis_data ble_svc_dis_data = {
28     .model_number      = MYNEWT_VAL(BLE_SVC_DIS_MODEL_NUMBER_DEFAULT),
29     .serial_number     = MYNEWT_VAL(BLE_SVC_DIS_SERIAL_NUMBER_DEFAULT),
30     .firmware_revision = MYNEWT_VAL(BLE_SVC_DIS_FIRMWARE_REVISION_DEFAULT),
31     .hardware_revision = MYNEWT_VAL(BLE_SVC_DIS_HARDWARE_REVISION_DEFAULT),
32     .software_revision = MYNEWT_VAL(BLE_SVC_DIS_SOFTWARE_REVISION_DEFAULT),
33     .manufacturer_name = MYNEWT_VAL(BLE_SVC_DIS_MANUFACTURER_NAME_DEFAULT),
34 };
35 
36 /* Access function */
37 #if (MYNEWT_VAL(BLE_SVC_DIS_MODEL_NUMBER_READ_PERM)      >= 0) ||	\
38     (MYNEWT_VAL(BLE_SVC_DIS_SERIAL_NUMBER_READ_PERM)     >= 0) ||	\
39     (MYNEWT_VAL(BLE_SVC_DIS_HARDWARE_REVISION_READ_PERM) >= 0) ||	\
40     (MYNEWT_VAL(BLE_SVC_DIS_FIRMWARE_REVISION_READ_PERM) >= 0) ||	\
41     (MYNEWT_VAL(BLE_SVC_DIS_SOFTWARE_REVISION_READ_PERM) >= 0) ||	\
42     (MYNEWT_VAL(BLE_SVC_DIS_MANUFACTURER_NAME_READ_PERM) >= 0)
43 static int
44 ble_svc_dis_access(uint16_t conn_handle, uint16_t attr_handle,
45                    struct ble_gatt_access_ctxt *ctxt, void *arg);
46 #endif
47 
48 static const struct ble_gatt_svc_def ble_svc_dis_defs[] = {
49     { /*** Service: Device Information Service (DIS). */
50         .type = BLE_GATT_SVC_TYPE_PRIMARY,
51         .uuid = BLE_UUID16_DECLARE(BLE_SVC_DIS_UUID16),
52         .characteristics = (struct ble_gatt_chr_def[]) { {
53 #if (MYNEWT_VAL(BLE_SVC_DIS_MODEL_NUMBER_READ_PERM) >= 0)
54 	    /*** Characteristic: Model Number String */
55             .uuid = BLE_UUID16_DECLARE(BLE_SVC_DIS_CHR_UUID16_MODEL_NUMBER),
56             .access_cb = ble_svc_dis_access,
57             .flags = BLE_GATT_CHR_F_READ |
58 	             MYNEWT_VAL(BLE_SVC_DIS_MODEL_NUMBER_READ_PERM),
59         }, {
60 #endif
61 #if (MYNEWT_VAL(BLE_SVC_DIS_SERIAL_NUMBER_READ_PERM) >= 0)
62 	    /*** Characteristic: Serial Number String */
63             .uuid = BLE_UUID16_DECLARE(BLE_SVC_DIS_CHR_UUID16_SERIAL_NUMBER),
64             .access_cb = ble_svc_dis_access,
65             .flags = BLE_GATT_CHR_F_READ |
66 	             MYNEWT_VAL(BLE_SVC_DIS_SERIAL_NUMBER_READ_PERM),
67         }, {
68 #endif
69 #if (MYNEWT_VAL(BLE_SVC_DIS_HARDWARE_REVISION_READ_PERM) >= 0)
70 	    /*** Characteristic: Hardware Revision String */
71             .uuid = BLE_UUID16_DECLARE(BLE_SVC_DIS_CHR_UUID16_HARDWARE_REVISION),
72             .access_cb = ble_svc_dis_access,
73             .flags = BLE_GATT_CHR_F_READ |
74 	             MYNEWT_VAL(BLE_SVC_DIS_HARDWARE_REVISION_READ_PERM),
75         }, {
76 #endif
77 #if (MYNEWT_VAL(BLE_SVC_DIS_FIRMWARE_REVISION_READ_PERM) >= 0)
78 	    /*** Characteristic: Firmware Revision String */
79             .uuid = BLE_UUID16_DECLARE(BLE_SVC_DIS_CHR_UUID16_FIRMWARE_REVISION),
80             .access_cb = ble_svc_dis_access,
81             .flags = BLE_GATT_CHR_F_READ |
82 	             MYNEWT_VAL(BLE_SVC_DIS_FIRMWARE_REVISION_READ_PERM),
83         }, {
84 #endif
85 #if (MYNEWT_VAL(BLE_SVC_DIS_SOFTWARE_REVISION_READ_PERM) >= 0)
86 	    /*** Characteristic: Software Revision String */
87             .uuid = BLE_UUID16_DECLARE(BLE_SVC_DIS_CHR_UUID16_SOFTWARE_REVISION),
88             .access_cb = ble_svc_dis_access,
89             .flags = BLE_GATT_CHR_F_READ |
90 	             MYNEWT_VAL(BLE_SVC_DIS_SOFTWARE_REVISION_READ_PERM),
91         }, {
92 #endif
93 #if (MYNEWT_VAL(BLE_SVC_DIS_MANUFACTURER_NAME_READ_PERM) >= 0)
94 	    /*** Characteristic: Manufacturer Name */
95             .uuid = BLE_UUID16_DECLARE(BLE_SVC_DIS_CHR_UUID16_MANUFACTURER_NAME),
96             .access_cb = ble_svc_dis_access,
97             .flags = BLE_GATT_CHR_F_READ |
98 	             MYNEWT_VAL(BLE_SVC_DIS_MANUFACTURER_NAME_READ_PERM),
99         }, {
100 #endif
101             0, /* No more characteristics in this service */
102         }, }
103     },
104 
105     {
106         0, /* No more services. */
107     },
108 };
109 
110 /**
111  * Simple read access callback for the device information service
112  * characteristic.
113  */
114 #if (MYNEWT_VAL(BLE_SVC_DIS_MODEL_NUMBER_READ_PERM)      >= 0) ||	\
115     (MYNEWT_VAL(BLE_SVC_DIS_SERIAL_NUMBER_READ_PERM)     >= 0) ||	\
116     (MYNEWT_VAL(BLE_SVC_DIS_HARDWARE_REVISION_READ_PERM) >= 0) ||	\
117     (MYNEWT_VAL(BLE_SVC_DIS_FIRMWARE_REVISION_READ_PERM) >= 0) ||	\
118     (MYNEWT_VAL(BLE_SVC_DIS_SOFTWARE_REVISION_READ_PERM) >= 0) ||	\
119     (MYNEWT_VAL(BLE_SVC_DIS_MANUFACTURER_NAME_READ_PERM) >= 0)
120 static int
ble_svc_dis_access(uint16_t conn_handle,uint16_t attr_handle,struct ble_gatt_access_ctxt * ctxt,void * arg)121 ble_svc_dis_access(uint16_t conn_handle, uint16_t attr_handle,
122                    struct ble_gatt_access_ctxt *ctxt, void *arg)
123 {
124     uint16_t uuid    = ble_uuid_u16(ctxt->chr->uuid);
125     const char *info = NULL;
126 
127     switch(uuid) {
128 #if (MYNEWT_VAL(BLE_SVC_DIS_MODEL_NUMBER_READ_PERM) >= 0)
129     case BLE_SVC_DIS_CHR_UUID16_MODEL_NUMBER:
130 	info = ble_svc_dis_data.model_number;
131 #ifdef MYNEWT_VAL_BLE_SVC_DIS_MODEL_NUMBER_NAME_DEFAULT
132 	if (info == NULL) {
133 	    info = MYNEWT_VAL(BLE_SVC_DIS_MODEL_NUMBER_DEFAULT);
134 	}
135 #endif
136 	break;
137 #endif
138 #if (MYNEWT_VAL(BLE_SVC_DIS_SERIAL_NUMBER_READ_PERM) >= 0)
139     case BLE_SVC_DIS_CHR_UUID16_SERIAL_NUMBER:
140 	info = ble_svc_dis_data.serial_number;
141 #ifdef MYNEWT_VAL_BLE_SVC_DIS_SERIAL_NUMBER_DEFAULT
142 	if (info == NULL) {
143 	    info = MYNEWT_VAL(BLE_SVC_DIS_SERIAL_NUMBER_DEFAULT);
144 	}
145 #endif
146 	break;
147 #endif
148 #if (MYNEWT_VAL(BLE_SVC_DIS_FIRMWARE_REVISION_READ_PERM) >= 0)
149     case BLE_SVC_DIS_CHR_UUID16_FIRMWARE_REVISION:
150 	info = ble_svc_dis_data.firmware_revision;
151 #ifdef MYNEWT_VAL_BLE_SVC_DIS_FIRMWARE_REVISION_DEFAULT
152 	if (info == NULL) {
153 	    info = MYNEWT_VAL(BLE_SVC_DIS_FIRMWARE_REVISION_DEFAULT);
154 	}
155 #endif
156 	break;
157 #endif
158 #if (MYNEWT_VAL(BLE_SVC_DIS_HARDWARE_REVISION_READ_PERM) >= 0)
159     case BLE_SVC_DIS_CHR_UUID16_HARDWARE_REVISION:
160 	info = ble_svc_dis_data.hardware_revision;
161 #ifdef MYNEWT_VAL_BLE_SVC_DIS_HARDWARE_REVISION_DEFAULT
162 	if (info == NULL) {
163 	    info = MYNEWT_VAL(BLE_SVC_DIS_HARDWARE_REVISION_DEFAULT);
164 	}
165 #endif
166 	break;
167 #endif
168 #if (MYNEWT_VAL(BLE_SVC_DIS_SOFTWARE_REVISION_READ_PERM) >= 0)
169     case BLE_SVC_DIS_CHR_UUID16_SOFTWARE_REVISION:
170 	info = ble_svc_dis_data.software_revision;
171 #ifdef MYNEWT_VAL_BLE_SVC_DIS_SOFTWARE_REVISION_DEFAULT
172 	if (info == NULL) {
173 	    info = MYNEWT_VAL(BLE_SVC_DIS_SOFTWARE_REVISION_DEFAULT);
174 	}
175 #endif
176 	break;
177 #endif
178 #if (MYNEWT_VAL(BLE_SVC_DIS_MANUFACTURER_NAME_READ_PERM) >= 0)
179     case BLE_SVC_DIS_CHR_UUID16_MANUFACTURER_NAME:
180 	info = ble_svc_dis_data.manufacturer_name;
181 #ifdef MYNEWT_VAL_BLE_SVC_DIS_MANUFACTURER_NAME_DEFAULT
182 	if (info == NULL) {
183 	    info = MYNEWT_VAL(BLE_SVC_DIS_MANUFACTURER_NAME_DEFAULT);
184 	}
185 #endif
186 	break;
187 #endif
188     default:
189 	assert(0);
190 	return BLE_ATT_ERR_UNLIKELY;
191     }
192 
193     if (info != NULL) {
194 	int rc = os_mbuf_append(ctxt->om, info, strlen(info));
195 	return rc == 0 ? 0 : BLE_ATT_ERR_INSUFFICIENT_RES;
196     }
197 
198     return 0;
199 }
200 #endif
201 
202 const char *
ble_svc_dis_model_number(void)203 ble_svc_dis_model_number(void)
204 {
205     return ble_svc_dis_data.model_number;
206 }
207 
208 int
ble_svc_dis_model_number_set(const char * value)209 ble_svc_dis_model_number_set(const char *value)
210 {
211     ble_svc_dis_data.model_number = value;
212     return 0;
213 }
214 
215 const char *
ble_svc_dis_serial_number(void)216 ble_svc_dis_serial_number(void)
217 {
218     return ble_svc_dis_data.serial_number;
219 }
220 
221 int
ble_svc_dis_serial_number_set(const char * value)222 ble_svc_dis_serial_number_set(const char *value)
223 {
224     ble_svc_dis_data.serial_number = value;
225     return 0;
226 }
227 
228 const char *
ble_svc_dis_firmware_revision(void)229 ble_svc_dis_firmware_revision(void)
230 {
231     return ble_svc_dis_data.firmware_revision;
232 }
233 
234 int
ble_svc_dis_firmware_revision_set(const char * value)235 ble_svc_dis_firmware_revision_set(const char *value)
236 {
237     ble_svc_dis_data.firmware_revision = value;
238     return 0;
239 }
240 
241 const char *
ble_svc_dis_hardware_revision(void)242 ble_svc_dis_hardware_revision(void)
243 {
244     return ble_svc_dis_data.hardware_revision;
245 }
246 
247 int
ble_svc_dis_hardware_revision_set(const char * value)248 ble_svc_dis_hardware_revision_set(const char *value)
249 {
250     ble_svc_dis_data.hardware_revision = value;
251     return 0;
252 }
253 
254 const char *
ble_svc_dis_software_revision(void)255 ble_svc_dis_software_revision(void)
256 {
257     return ble_svc_dis_data.software_revision;
258 }
259 
260 int
ble_svc_dis_software_revision_set(const char * value)261 ble_svc_dis_software_revision_set(const char *value)
262 {
263     ble_svc_dis_data.software_revision = value;
264     return 0;
265 }
266 
267 const char *
ble_svc_dis_manufacturer_name(void)268 ble_svc_dis_manufacturer_name(void)
269 {
270     return ble_svc_dis_data.manufacturer_name;
271 }
272 
273 int
ble_svc_dis_manufacturer_name_set(const char * value)274 ble_svc_dis_manufacturer_name_set(const char *value)
275 {
276     ble_svc_dis_data.manufacturer_name = value;
277     return 0;
278 }
279 
280 /**
281  * Initialize the DIS package.
282  */
283 void
ble_svc_dis_init(void)284 ble_svc_dis_init(void)
285 {
286     int rc;
287 
288     /* Ensure this function only gets called by sysinit. */
289     SYSINIT_ASSERT_ACTIVE();
290 
291     rc = ble_gatts_count_cfg(ble_svc_dis_defs);
292     SYSINIT_PANIC_ASSERT(rc == 0);
293 
294     rc = ble_gatts_add_svcs(ble_svc_dis_defs);
295     SYSINIT_PANIC_ASSERT(rc == 0);
296 }
297