1 /******************************************************************************
2 *
3 * Copyright (C) 2010-2012 Broadcom Corporation
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at:
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 ******************************************************************************/
18
19 /******************************************************************************
20 *
21 * This is the implementation of the API for GATT server of BTA.
22 *
23 ******************************************************************************/
24
25 #include "bt_target.h"
26
27 #if defined(BTA_GATT_INCLUDED) && (BTA_GATT_INCLUDED == TRUE)
28
29 #include <string.h>
30 #include "gki.h"
31 #include "bta_sys.h"
32 #include "bta_gatt_api.h"
33 #include "bta_gatts_int.h"
34
35 /*****************************************************************************
36 ** Constants
37 *****************************************************************************/
38
39 static const tBTA_SYS_REG bta_gatts_reg =
40 {
41 bta_gatts_hdl_event,
42 BTA_GATTS_Disable
43 };
44
45 /*******************************************************************************
46 **
47 ** Function BTA_GATTS_Disable
48 **
49 ** Description This function is called to disable GATTS module
50 **
51 ** Parameters None.
52 **
53 ** Returns None
54 **
55 *******************************************************************************/
BTA_GATTS_Disable(void)56 void BTA_GATTS_Disable(void)
57 {
58 BT_HDR *p_buf;
59
60 if (bta_sys_is_register(BTA_ID_GATTS) == FALSE)
61 {
62 APPL_TRACE_WARNING("GATTS Module not enabled/already disabled");
63 return;
64 }
65
66 if ((p_buf = (BT_HDR *) GKI_getbuf(sizeof(BT_HDR))) != NULL)
67 {
68 p_buf->event = BTA_GATTS_API_DISABLE_EVT;
69 bta_sys_sendmsg(p_buf);
70 }
71 bta_sys_deregister(BTA_ID_GATTS);
72
73 }
74
75 /*******************************************************************************
76 **
77 ** Function BTA_GATTS_AppRegister
78 **
79 ** Description This function is called to register application callbacks
80 ** with BTA GATTS module.
81 **
82 ** Parameters p_app_uuid - applicaiton UUID
83 ** p_cback - pointer to the application callback function.
84 **
85 ** Returns None
86 **
87 *******************************************************************************/
BTA_GATTS_AppRegister(tBT_UUID * p_app_uuid,tBTA_GATTS_CBACK * p_cback)88 void BTA_GATTS_AppRegister(tBT_UUID *p_app_uuid, tBTA_GATTS_CBACK *p_cback)
89 {
90 tBTA_GATTS_API_REG *p_buf;
91
92 /* register with BTA system manager */
93 if (bta_sys_is_register(BTA_ID_GATTS) == FALSE)
94 {
95 bta_sys_register(BTA_ID_GATTS, &bta_gatts_reg);
96 }
97
98 if ((p_buf = (tBTA_GATTS_API_REG *) GKI_getbuf(sizeof(tBTA_GATTS_API_REG))) != NULL)
99 {
100 p_buf->hdr.event = BTA_GATTS_API_REG_EVT;
101
102 if (p_app_uuid != NULL)
103 memcpy(&p_buf->app_uuid, p_app_uuid, sizeof(tBT_UUID));
104 p_buf->p_cback = p_cback;
105
106 bta_sys_sendmsg(p_buf);
107 }
108 return;
109 }
110
111
112
113 /*******************************************************************************
114 **
115 ** Function BTA_GATTS_AppDeregister
116 **
117 ** Description De-register with GATT Server.
118 **
119 ** Parameters app_id: applicatino ID.
120 **
121 ** Returns void
122 **
123 *******************************************************************************/
BTA_GATTS_AppDeregister(tBTA_GATTS_IF server_if)124 void BTA_GATTS_AppDeregister(tBTA_GATTS_IF server_if)
125 {
126 tBTA_GATTS_API_DEREG *p_buf;
127
128 if ((p_buf = (tBTA_GATTS_API_DEREG *) GKI_getbuf(sizeof(tBTA_GATTS_API_DEREG))) != NULL)
129 {
130 p_buf->hdr.event = BTA_GATTS_API_DEREG_EVT;
131 p_buf->server_if = server_if;
132
133 bta_sys_sendmsg(p_buf);
134 }
135 return;
136 }
137
138 /*******************************************************************************
139 **
140 ** Function BTA_GATTS_CreateService
141 **
142 ** Description Create a service. When service creation is done, a callback
143 ** event BTA_GATTS_CREATE_SRVC_EVT is called to report status
144 ** and service ID to the profile. The service ID obtained in
145 ** the callback function needs to be used when adding included
146 ** service and characteristics/descriptors into the service.
147 **
148 ** Parameters app_id: Profile ID this service is belonged to.
149 ** p_service_uuid: service UUID.
150 ** inst: instance ID number of this service.
151 ** num_handle: numble of handle requessted for this service.
152 ** is_primary: is this service a primary one or not.
153 **
154 ** Returns void
155 **
156 *******************************************************************************/
BTA_GATTS_CreateService(tBTA_GATTS_IF server_if,tBT_UUID * p_service_uuid,UINT8 inst,UINT16 num_handle,BOOLEAN is_primary)157 void BTA_GATTS_CreateService(tBTA_GATTS_IF server_if, tBT_UUID *p_service_uuid, UINT8 inst,
158 UINT16 num_handle, BOOLEAN is_primary)
159 {
160 tBTA_GATTS_API_CREATE_SRVC *p_buf;
161
162 if ((p_buf = (tBTA_GATTS_API_CREATE_SRVC *) GKI_getbuf(sizeof(tBTA_GATTS_API_CREATE_SRVC))) != NULL)
163 {
164 p_buf->hdr.event = BTA_GATTS_API_CREATE_SRVC_EVT;
165
166 p_buf->server_if = server_if;
167 p_buf->inst = inst;
168 memcpy(&p_buf->service_uuid, p_service_uuid, sizeof(tBT_UUID));
169 p_buf->num_handle = num_handle;
170 p_buf->is_pri = is_primary;
171
172 bta_sys_sendmsg(p_buf);
173 }
174 return;
175 }
176 /*******************************************************************************
177 **
178 ** Function BTA_GATTS_AddIncludeService
179 **
180 ** Description This function is called to add an included service. After included
181 ** service is included, a callback event BTA_GATTS_ADD_INCL_SRVC_EVT
182 ** is reported the included service ID.
183 **
184 ** Parameters service_id: service ID to which this included service is to
185 ** be added.
186 ** included_service_id: the service ID to be included.
187 **
188 ** Returns void
189 **
190 *******************************************************************************/
BTA_GATTS_AddIncludeService(UINT16 service_id,UINT16 included_service_id)191 void BTA_GATTS_AddIncludeService(UINT16 service_id, UINT16 included_service_id)
192 {
193 tBTA_GATTS_API_ADD_INCL_SRVC *p_buf;
194
195 if ((p_buf =
196 (tBTA_GATTS_API_ADD_INCL_SRVC *) GKI_getbuf(sizeof(tBTA_GATTS_API_ADD_INCL_SRVC)))
197 != NULL)
198 {
199 p_buf->hdr.event = BTA_GATTS_API_ADD_INCL_SRVC_EVT;
200
201 p_buf->hdr.layer_specific = service_id;
202 p_buf->included_service_id = included_service_id;
203
204 bta_sys_sendmsg(p_buf);
205 }
206 return;
207
208 }
209 /*******************************************************************************
210 **
211 ** Function BTA_GATTS_AddCharacteristic
212 **
213 ** Description This function is called to add a characteristic into a service.
214 **
215 ** Parameters service_id: service ID to which this included service is to
216 ** be added.
217 ** p_char_uuid : Characteristic UUID.
218 ** perm : Characteristic value declaration attribute permission.
219 ** property : Characteristic Properties
220 **
221 ** Returns None
222 **
223 *******************************************************************************/
BTA_GATTS_AddCharacteristic(UINT16 service_id,tBT_UUID * p_char_uuid,tBTA_GATT_PERM perm,tBTA_GATT_CHAR_PROP property)224 void BTA_GATTS_AddCharacteristic (UINT16 service_id, tBT_UUID *p_char_uuid,
225 tBTA_GATT_PERM perm, tBTA_GATT_CHAR_PROP property)
226 {
227 tBTA_GATTS_API_ADD_CHAR *p_buf;
228
229 if ((p_buf = (tBTA_GATTS_API_ADD_CHAR *) GKI_getbuf(sizeof(tBTA_GATTS_API_ADD_CHAR))) != NULL)
230 {
231 memset(p_buf, 0, sizeof(tBTA_GATTS_API_ADD_CHAR));
232
233 p_buf->hdr.event = BTA_GATTS_API_ADD_CHAR_EVT;
234 p_buf->hdr.layer_specific = service_id;
235 p_buf->perm = perm;
236 p_buf->property = property;
237
238 if (p_char_uuid)
239 {
240 memcpy(&p_buf->char_uuid, p_char_uuid, sizeof(tBT_UUID));
241 }
242 bta_sys_sendmsg(p_buf);
243 }
244 return;
245 }
246
247 /*******************************************************************************
248 **
249 ** Function BTA_GATTS_AddCharDescriptor
250 **
251 ** Description This function is called to add characteristic descriptor. When
252 ** it's done, a callback event BTA_GATTS_ADD_DESCR_EVT is called
253 ** to report the status and an ID number for this descriptor.
254 **
255 ** Parameters service_id: service ID to which this charatceristic descriptor is to
256 ** be added.
257 ** perm: descriptor access permission.
258 ** p_descr_uuid: descriptor UUID.
259 **
260 ** Returns returns status.
261 **
262 *******************************************************************************/
BTA_GATTS_AddCharDescriptor(UINT16 service_id,tBTA_GATT_PERM perm,tBT_UUID * p_descr_uuid)263 void BTA_GATTS_AddCharDescriptor (UINT16 service_id,
264 tBTA_GATT_PERM perm,
265 tBT_UUID * p_descr_uuid)
266 {
267 tBTA_GATTS_API_ADD_DESCR *p_buf;
268 UINT16 len = sizeof(tBTA_GATTS_API_ADD_DESCR);
269
270
271 if ((p_buf = (tBTA_GATTS_API_ADD_DESCR *) GKI_getbuf(len)) != NULL)
272 {
273 memset(p_buf, 0, len);
274
275 p_buf->hdr.event = BTA_GATTS_API_ADD_DESCR_EVT;
276 p_buf->hdr.layer_specific = service_id;
277 p_buf->perm = perm;
278
279 if (p_descr_uuid)
280 {
281 memcpy(&p_buf->descr_uuid, p_descr_uuid, sizeof(tBT_UUID));
282 }
283 bta_sys_sendmsg(p_buf);
284 }
285 return;
286
287 }
288
289 /*******************************************************************************
290 **
291 ** Function BTA_GATTS_DeleteService
292 **
293 ** Description This function is called to delete a service. When this is done,
294 ** a callback event BTA_GATTS_DELETE_EVT is report with the status.
295 **
296 ** Parameters service_id: service_id to be deleted.
297 **
298 ** Returns returns none.
299 **
300 *******************************************************************************/
BTA_GATTS_DeleteService(UINT16 service_id)301 void BTA_GATTS_DeleteService(UINT16 service_id)
302 {
303 BT_HDR *p_buf;
304
305 if ((p_buf = (BT_HDR *) GKI_getbuf(sizeof(BT_HDR))) != NULL)
306 {
307 p_buf->event = BTA_GATTS_API_DEL_SRVC_EVT;
308
309 p_buf->layer_specific = service_id;
310
311 bta_sys_sendmsg(p_buf);
312 }
313 return;
314
315 }
316
317 /*******************************************************************************
318 **
319 ** Function BTA_GATTS_StartService
320 **
321 ** Description This function is called to start a service.
322 **
323 ** Parameters service_id: the service ID to be started.
324 ** sup_transport: supported trasnport.
325 **
326 ** Returns None.
327 **
328 *******************************************************************************/
BTA_GATTS_StartService(UINT16 service_id,tBTA_GATT_TRANSPORT sup_transport)329 void BTA_GATTS_StartService(UINT16 service_id, tBTA_GATT_TRANSPORT sup_transport)
330 {
331 tBTA_GATTS_API_START *p_buf;
332
333 if ((p_buf = (tBTA_GATTS_API_START *) GKI_getbuf(sizeof(tBTA_GATTS_API_START))) != NULL)
334 {
335 p_buf->hdr.event = BTA_GATTS_API_START_SRVC_EVT;
336
337 p_buf->hdr.layer_specific = service_id;
338 p_buf->transport = sup_transport;
339
340 bta_sys_sendmsg(p_buf);
341 }
342 return;
343 }
344
345 /*******************************************************************************
346 **
347 ** Function BTA_GATTS_StopService
348 **
349 ** Description This function is called to stop a service.
350 **
351 ** Parameters service_id - service to be topped.
352 **
353 ** Returns None
354 **
355 *******************************************************************************/
BTA_GATTS_StopService(UINT16 service_id)356 void BTA_GATTS_StopService(UINT16 service_id)
357 {
358 BT_HDR *p_buf;
359
360 if ((p_buf = (BT_HDR *) GKI_getbuf(sizeof(BT_HDR))) != NULL)
361 {
362 p_buf->event = BTA_GATTS_API_STOP_SRVC_EVT;
363
364 p_buf->layer_specific = service_id;
365
366 bta_sys_sendmsg(p_buf);
367 }
368 return;
369 }
370
371 /*******************************************************************************
372 **
373 ** Function BTA_GATTS_HandleValueIndication
374 **
375 ** Description This function is called to read a characteristics descriptor.
376 **
377 ** Parameters bda - remote device bd address to indicate.
378 ** attr_id - attribute ID to indicate.
379 ** data_len - indicate data length.
380 ** p_data: data to indicate.
381 ** need_confirm - if this indication expects a confirmation or not.
382 **
383 ** Returns None
384 **
385 *******************************************************************************/
BTA_GATTS_HandleValueIndication(UINT16 conn_id,UINT16 attr_id,UINT16 data_len,UINT8 * p_data,BOOLEAN need_confirm)386 void BTA_GATTS_HandleValueIndication (UINT16 conn_id, UINT16 attr_id, UINT16 data_len,
387 UINT8 *p_data, BOOLEAN need_confirm)
388 {
389 tBTA_GATTS_API_INDICATION *p_buf;
390 UINT16 len = sizeof(tBTA_GATTS_API_INDICATION);
391
392 if ((p_buf = (tBTA_GATTS_API_INDICATION *) GKI_getbuf(len)) != NULL)
393 {
394 memset(p_buf, 0, len);
395
396 p_buf->hdr.event = BTA_GATTS_API_INDICATION_EVT;
397 p_buf->hdr.layer_specific = conn_id;
398 p_buf->attr_id = attr_id;
399 p_buf->need_confirm = need_confirm;
400
401 if (data_len > 0 && p_data != NULL)
402 {
403 p_buf->len = data_len;
404 memcpy(p_buf->value, p_data, data_len);
405
406 }
407 bta_sys_sendmsg(p_buf);
408 }
409 return;
410
411 }
412 /*******************************************************************************
413 **
414 ** Function BTA_GATTS_SendRsp
415 **
416 ** Description This function is called to send a response to a request.
417 **
418 ** Parameters conn_id - connection identifier.
419 ** trans_id - transaction ID.
420 ** status - response status
421 ** p_msg - response data.
422 **
423 ** Returns None
424 **
425 *******************************************************************************/
BTA_GATTS_SendRsp(UINT16 conn_id,UINT32 trans_id,tBTA_GATT_STATUS status,tBTA_GATTS_RSP * p_msg)426 void BTA_GATTS_SendRsp (UINT16 conn_id, UINT32 trans_id,
427 tBTA_GATT_STATUS status, tBTA_GATTS_RSP *p_msg)
428 {
429 tBTA_GATTS_API_RSP *p_buf;
430 UINT16 len = sizeof(tBTA_GATTS_API_RSP) + sizeof(tBTA_GATTS_RSP);
431
432 if ((p_buf = (tBTA_GATTS_API_RSP *) GKI_getbuf(len)) != NULL)
433 {
434 memset(p_buf, 0, len);
435
436 p_buf->hdr.event = BTA_GATTS_API_RSP_EVT;
437 p_buf->hdr.layer_specific = conn_id;
438 p_buf->trans_id = trans_id;
439 p_buf->status = status;
440
441 if (p_msg != NULL)
442 {
443 p_buf->p_rsp = (tBTA_GATTS_RSP *)(p_buf + 1);
444 memcpy(p_buf->p_rsp, p_msg, sizeof(tBTA_GATTS_RSP));
445 }
446
447 bta_sys_sendmsg(p_buf);
448 }
449 return;
450
451 }
452
453
454
455 /*******************************************************************************
456 **
457 ** Function BTA_GATTS_Open
458 **
459 ** Description Open a direct open connection or add a background auto connection
460 ** bd address
461 **
462 ** Parameters server_if: server interface.
463 ** remote_bda: remote device BD address.
464 ** is_direct: direct connection or background auto connection
465 ** transport : Transport on which GATT connection to be opened (BR/EDR or LE)
466 **
467 ** Returns void
468 **
469 *******************************************************************************/
BTA_GATTS_Open(tBTA_GATTS_IF server_if,BD_ADDR remote_bda,BOOLEAN is_direct,tBTA_GATT_TRANSPORT transport)470 void BTA_GATTS_Open(tBTA_GATTS_IF server_if, BD_ADDR remote_bda, BOOLEAN is_direct,
471 tBTA_GATT_TRANSPORT transport)
472 {
473 tBTA_GATTS_API_OPEN *p_buf;
474
475 if ((p_buf = (tBTA_GATTS_API_OPEN *) GKI_getbuf(sizeof(tBTA_GATTS_API_OPEN))) != NULL)
476 {
477 p_buf->hdr.event = BTA_GATTS_API_OPEN_EVT;
478 p_buf->server_if = server_if;
479 p_buf->is_direct = is_direct;
480 p_buf->transport = transport;
481 memcpy(p_buf->remote_bda, remote_bda, BD_ADDR_LEN);
482
483 bta_sys_sendmsg(p_buf);
484 }
485 return;
486 }
487
488
489 /*******************************************************************************
490 **
491 ** Function BTA_GATTS_CancelOpen
492 **
493 ** Description Cancel a direct open connection or remove a background auto connection
494 ** bd address
495 **
496 ** Parameters server_if: server interface.
497 ** remote_bda: remote device BD address.
498 ** is_direct: direct connection or background auto connection
499 **
500 ** Returns void
501 **
502 *******************************************************************************/
BTA_GATTS_CancelOpen(tBTA_GATTS_IF server_if,BD_ADDR remote_bda,BOOLEAN is_direct)503 void BTA_GATTS_CancelOpen(tBTA_GATTS_IF server_if, BD_ADDR remote_bda, BOOLEAN is_direct)
504 {
505 tBTA_GATTS_API_CANCEL_OPEN *p_buf;
506
507 if ((p_buf = (tBTA_GATTS_API_CANCEL_OPEN *) GKI_getbuf(sizeof(tBTA_GATTS_API_CANCEL_OPEN))) != NULL)
508 {
509 p_buf->hdr.event = BTA_GATTS_API_CANCEL_OPEN_EVT;
510 p_buf->server_if = server_if;
511 p_buf->is_direct = is_direct;
512 memcpy(p_buf->remote_bda, remote_bda, BD_ADDR_LEN);
513 bta_sys_sendmsg(p_buf);
514 }
515 return;
516 }
517
518 /*******************************************************************************
519 **
520 ** Function BTA_GATTS_Close
521 **
522 ** Description Close a connection a remote device.
523 **
524 ** Parameters conn_id: connectino ID to be closed.
525 **
526 ** Returns void
527 **
528 *******************************************************************************/
BTA_GATTS_Close(UINT16 conn_id)529 void BTA_GATTS_Close(UINT16 conn_id)
530 {
531 BT_HDR *p_buf;
532
533 if ((p_buf = (BT_HDR *) GKI_getbuf(sizeof(BT_HDR))) != NULL)
534 {
535 p_buf->event = BTA_GATTS_API_CLOSE_EVT;
536 p_buf->layer_specific = conn_id;
537 bta_sys_sendmsg(p_buf);
538 }
539 return;
540
541 }
542 /*******************************************************************************
543 **
544 ** Function BTA_GATTS_Listen
545 **
546 ** Description Start advertisement to listen for connection request for a
547 ** GATT server
548 **
549 ** Parameters server_if: server interface.
550 ** start: to start or stop listening for connection
551 ** remote_bda: remote device BD address, if listen to all device
552 ** use NULL.
553 **
554 ** Returns void
555 **
556 *******************************************************************************/
BTA_GATTS_Listen(tBTA_GATTS_IF server_if,BOOLEAN start,BD_ADDR_PTR target_bda)557 void BTA_GATTS_Listen(tBTA_GATTS_IF server_if, BOOLEAN start, BD_ADDR_PTR target_bda)
558 {
559 tBTA_GATTS_API_LISTEN *p_buf;
560
561 if ((p_buf = (tBTA_GATTS_API_LISTEN *) GKI_getbuf((UINT16)(sizeof(tBTA_GATTS_API_LISTEN) + BD_ADDR_LEN))) != NULL)
562 {
563 p_buf->hdr.event = BTA_GATTS_API_LISTEN_EVT;
564
565 p_buf->server_if = server_if;
566 p_buf->start = start;
567
568 if (target_bda)
569 {
570 p_buf->remote_bda = (UINT8*)(p_buf + 1);
571 memcpy(p_buf->remote_bda, target_bda, BD_ADDR_LEN);
572 }
573 else
574 p_buf->remote_bda = NULL;
575
576 bta_sys_sendmsg(p_buf);
577 }
578 return;
579 }
580
581 #endif /* BTA_GATT_INCLUDED */
582