• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /******************************************************************************
2  *
3  *  Copyright 1999-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 file contains the main GATT client functions
22  *
23  ******************************************************************************/
24 
25 #include "bt_target.h"
26 
27 #include <string.h>
28 #include "bt_common.h"
29 #include "bt_utils.h"
30 #include "gatt_int.h"
31 #include "l2c_int.h"
32 #include "log/log.h"
33 #include "osi/include/osi.h"
34 
35 #define GATT_WRITE_LONG_HDR_SIZE 5 /* 1 opcode + 2 handle + 2 offset */
36 #define GATT_READ_CHAR_VALUE_HDL (GATT_READ_CHAR_VALUE | 0x80)
37 #define GATT_READ_INC_SRV_UUID128 (GATT_DISC_INC_SRVC | 0x90)
38 
39 #define GATT_PREP_WRITE_RSP_MIN_LEN 4
40 #define GATT_NOTIFICATION_MIN_LEN 2
41 #define GATT_WRITE_RSP_MIN_LEN 2
42 #define GATT_INFO_RSP_MIN_LEN 1
43 #define GATT_MTU_RSP_MIN_LEN 2
44 #define GATT_READ_BY_TYPE_RSP_MIN_LEN 1
45 
46 using base::StringPrintf;
47 using bluetooth::Uuid;
48 
49 /*******************************************************************************
50  *                      G L O B A L      G A T T       D A T A                 *
51  ******************************************************************************/
52 void gatt_send_prepare_write(tGATT_TCB& tcb, tGATT_CLCB* p_clcb);
53 
54 uint8_t disc_type_to_att_opcode[GATT_DISC_MAX] = {
55     0,
56     GATT_REQ_READ_BY_GRP_TYPE, /*  GATT_DISC_SRVC_ALL = 1, */
57     GATT_REQ_FIND_TYPE_VALUE,  /*  GATT_DISC_SRVC_BY_UUID,  */
58     GATT_REQ_READ_BY_TYPE,     /*  GATT_DISC_INC_SRVC,      */
59     GATT_REQ_READ_BY_TYPE,     /*  GATT_DISC_CHAR,          */
60     GATT_REQ_FIND_INFO         /*  GATT_DISC_CHAR_DSCPT,    */
61 };
62 
63 uint16_t disc_type_to_uuid[GATT_DISC_MAX] = {
64     0,                         /* reserved */
65     GATT_UUID_PRI_SERVICE,     /* <service> DISC_SRVC_ALL */
66     GATT_UUID_PRI_SERVICE,     /* <service> for DISC_SERVC_BY_UUID */
67     GATT_UUID_INCLUDE_SERVICE, /* <include_service> for DISC_INC_SRVC */
68     GATT_UUID_CHAR_DECLARE,    /* <characteristic> for DISC_CHAR */
69     0                          /* no type filtering for DISC_CHAR_DSCPT */
70 };
71 
72 /*******************************************************************************
73  *
74  * Function         gatt_act_discovery
75  *
76  * Description      GATT discovery operation.
77  *
78  * Returns          void.
79  *
80  ******************************************************************************/
gatt_act_discovery(tGATT_CLCB * p_clcb)81 void gatt_act_discovery(tGATT_CLCB* p_clcb) {
82   uint8_t op_code = disc_type_to_att_opcode[p_clcb->op_subtype];
83 
84   if (p_clcb->s_handle > p_clcb->e_handle || p_clcb->s_handle == 0) {
85     /* end of handle range */
86     gatt_end_operation(p_clcb, GATT_SUCCESS, NULL);
87     return;
88   }
89 
90   tGATT_CL_MSG cl_req;
91   memset(&cl_req, 0, sizeof(tGATT_CL_MSG));
92 
93   cl_req.browse.s_handle = p_clcb->s_handle;
94   cl_req.browse.e_handle = p_clcb->e_handle;
95 
96   if (disc_type_to_uuid[p_clcb->op_subtype] != 0) {
97     cl_req.browse.uuid =
98         bluetooth::Uuid::From16Bit(disc_type_to_uuid[p_clcb->op_subtype]);
99   }
100 
101   if (p_clcb->op_subtype ==
102       GATT_DISC_SRVC_BY_UUID) /* fill in the FindByTypeValue request info*/
103   {
104     cl_req.find_type_value.uuid =
105         bluetooth::Uuid::From16Bit(disc_type_to_uuid[p_clcb->op_subtype]);
106     cl_req.find_type_value.s_handle = p_clcb->s_handle;
107     cl_req.find_type_value.e_handle = p_clcb->e_handle;
108 
109     size_t size = p_clcb->uuid.GetShortestRepresentationSize();
110     cl_req.find_type_value.value_len = size;
111     if (size == Uuid::kNumBytes16) {
112       uint8_t* p = cl_req.find_type_value.value;
113       UINT16_TO_STREAM(p, p_clcb->uuid.As16Bit());
114     } else if (size == Uuid::kNumBytes32) {
115       /* if service type is 32 bits UUID, convert it now */
116       memcpy(cl_req.find_type_value.value, p_clcb->uuid.To128BitLE().data(),
117             Uuid::kNumBytes128);
118       cl_req.find_type_value.value_len = Uuid::kNumBytes128;
119     } else
120       memcpy(cl_req.find_type_value.value, p_clcb->uuid.To128BitLE().data(),
121              size);
122   }
123 
124   tGATT_STATUS st = attp_send_cl_msg(*p_clcb->p_tcb, p_clcb, op_code, &cl_req);
125   if (st != GATT_SUCCESS && st != GATT_CMD_STARTED) {
126     gatt_end_operation(p_clcb, GATT_ERROR, NULL);
127   }
128 }
129 
130 /*******************************************************************************
131  *
132  * Function         gatt_act_read
133  *
134  * Description      GATT read operation.
135  *
136  * Returns          void.
137  *
138  ******************************************************************************/
gatt_act_read(tGATT_CLCB * p_clcb,uint16_t offset)139 void gatt_act_read(tGATT_CLCB* p_clcb, uint16_t offset) {
140   tGATT_TCB& tcb = *p_clcb->p_tcb;
141   uint8_t rt = GATT_INTERNAL_ERROR;
142   tGATT_CL_MSG msg;
143   uint8_t op_code = 0;
144 
145   memset(&msg, 0, sizeof(tGATT_CL_MSG));
146 
147   switch (p_clcb->op_subtype) {
148     case GATT_READ_CHAR_VALUE:
149     case GATT_READ_BY_TYPE:
150       op_code = GATT_REQ_READ_BY_TYPE;
151       msg.browse.s_handle = p_clcb->s_handle;
152       msg.browse.e_handle = p_clcb->e_handle;
153       if (p_clcb->op_subtype == GATT_READ_BY_TYPE)
154         msg.browse.uuid = p_clcb->uuid;
155       else {
156         msg.browse.uuid = bluetooth::Uuid::From16Bit(GATT_UUID_CHAR_DECLARE);
157       }
158       break;
159 
160     case GATT_READ_CHAR_VALUE_HDL:
161     case GATT_READ_BY_HANDLE:
162       if (!p_clcb->counter) {
163         op_code = GATT_REQ_READ;
164         msg.handle = p_clcb->s_handle;
165       } else {
166         if (!p_clcb->first_read_blob_after_read)
167           p_clcb->first_read_blob_after_read = true;
168         else
169           p_clcb->first_read_blob_after_read = false;
170 
171         VLOG(1) << __func__ << ": first_read_blob_after_read="
172                 << p_clcb->first_read_blob_after_read;
173         op_code = GATT_REQ_READ_BLOB;
174         msg.read_blob.offset = offset;
175         msg.read_blob.handle = p_clcb->s_handle;
176       }
177       p_clcb->op_subtype &= ~0x80;
178       break;
179 
180     case GATT_READ_PARTIAL:
181       op_code = GATT_REQ_READ_BLOB;
182       msg.read_blob.handle = p_clcb->s_handle;
183       msg.read_blob.offset = offset;
184       break;
185 
186     case GATT_READ_MULTIPLE:
187       op_code = GATT_REQ_READ_MULTI;
188       memcpy(&msg.read_multi, p_clcb->p_attr_buf, sizeof(tGATT_READ_MULTI));
189       break;
190 
191     case GATT_READ_INC_SRV_UUID128:
192       op_code = GATT_REQ_READ;
193       msg.handle = p_clcb->s_handle;
194       p_clcb->op_subtype &= ~0x90;
195       break;
196 
197     default:
198       LOG(ERROR) << "Unknown read type:" << +p_clcb->op_subtype;
199       break;
200   }
201 
202   if (op_code != 0) rt = attp_send_cl_msg(tcb, p_clcb, op_code, &msg);
203 
204   if (op_code == 0 || (rt != GATT_SUCCESS && rt != GATT_CMD_STARTED)) {
205     gatt_end_operation(p_clcb, rt, NULL);
206   }
207 }
208 
209 /** GATT write operation */
gatt_act_write(tGATT_CLCB * p_clcb,uint8_t sec_act)210 void gatt_act_write(tGATT_CLCB* p_clcb, uint8_t sec_act) {
211   tGATT_TCB& tcb = *p_clcb->p_tcb;
212 
213   CHECK(p_clcb->p_attr_buf);
214   tGATT_VALUE& attr = *((tGATT_VALUE*)p_clcb->p_attr_buf);
215 
216   switch (p_clcb->op_subtype) {
217     case GATT_WRITE_NO_RSP: {
218       p_clcb->s_handle = attr.handle;
219       uint8_t op_code = (sec_act == GATT_SEC_SIGN_DATA) ? GATT_SIGN_CMD_WRITE
220                                                         : GATT_CMD_WRITE;
221       uint8_t rt = gatt_send_write_msg(tcb, p_clcb, op_code, attr.handle,
222                                        attr.len, 0, attr.value);
223       if (rt != GATT_CMD_STARTED) {
224         if (rt != GATT_SUCCESS) {
225           LOG(ERROR) << StringPrintf(
226               "gatt_act_write() failed op_code=0x%x rt=%d", op_code, rt);
227         }
228         gatt_end_operation(p_clcb, rt, NULL);
229       }
230       return;
231     }
232 
233     case GATT_WRITE: {
234       if (attr.len <= (tcb.payload_size - GATT_HDR_SIZE)) {
235         p_clcb->s_handle = attr.handle;
236 
237         uint8_t rt = gatt_send_write_msg(tcb, p_clcb, GATT_REQ_WRITE,
238                                          attr.handle, attr.len, 0, attr.value);
239         if (rt != GATT_SUCCESS && rt != GATT_CMD_STARTED &&
240             rt != GATT_CONGESTED) {
241           if (rt != GATT_SUCCESS) {
242             LOG(ERROR) << StringPrintf(
243                 "gatt_act_write() failed op_code=0x%x rt=%d", GATT_REQ_WRITE,
244                 rt);
245           }
246           gatt_end_operation(p_clcb, rt, NULL);
247         }
248 
249       } else {
250         /* prepare write for long attribute */
251         gatt_send_prepare_write(tcb, p_clcb);
252       }
253       return;
254     }
255 
256     case GATT_WRITE_PREPARE:
257       gatt_send_prepare_write(tcb, p_clcb);
258       return;
259 
260     default:
261       CHECK(false) << "Unknown write type" << p_clcb->op_subtype;
262       return;
263   }
264 }
265 /*******************************************************************************
266  *
267  * Function         gatt_send_queue_write_cancel
268  *
269  * Description      send queue write cancel
270  *
271  * Returns          void.
272  *
273  ******************************************************************************/
gatt_send_queue_write_cancel(tGATT_TCB & tcb,tGATT_CLCB * p_clcb,tGATT_EXEC_FLAG flag)274 void gatt_send_queue_write_cancel(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
275                                   tGATT_EXEC_FLAG flag) {
276   uint8_t rt;
277 
278   VLOG(1) << __func__;
279 
280   tGATT_CL_MSG gatt_cl_msg;
281   gatt_cl_msg.exec_write = flag;
282   rt = attp_send_cl_msg(tcb, p_clcb, GATT_REQ_EXEC_WRITE, &gatt_cl_msg);
283 
284   if (rt != GATT_SUCCESS) {
285     gatt_end_operation(p_clcb, rt, NULL);
286   }
287 }
288 /*******************************************************************************
289  *
290  * Function         gatt_check_write_long_terminate
291  *
292  * Description      To terminate write long or not.
293  *
294  * Returns          true: write long is terminated; false keep sending.
295  *
296  ******************************************************************************/
gatt_check_write_long_terminate(tGATT_TCB & tcb,tGATT_CLCB * p_clcb,tGATT_VALUE * p_rsp_value)297 bool gatt_check_write_long_terminate(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
298                                      tGATT_VALUE* p_rsp_value) {
299   tGATT_VALUE* p_attr = (tGATT_VALUE*)p_clcb->p_attr_buf;
300   bool exec = false;
301   tGATT_EXEC_FLAG flag = GATT_PREP_WRITE_EXEC;
302 
303   VLOG(1) << __func__;
304   /* check the first write response status */
305   if (p_rsp_value != NULL) {
306     if (p_rsp_value->handle != p_attr->handle ||
307         p_rsp_value->len != p_clcb->counter ||
308         memcmp(p_rsp_value->value, p_attr->value + p_attr->offset,
309                p_rsp_value->len)) {
310       /* data does not match    */
311       p_clcb->status = GATT_ERROR;
312       flag = GATT_PREP_WRITE_CANCEL;
313       exec = true;
314     } else /* response checking is good */
315     {
316       p_clcb->status = GATT_SUCCESS;
317       /* update write offset and check if end of attribute value */
318       if ((p_attr->offset += p_rsp_value->len) >= p_attr->len) exec = true;
319     }
320   }
321   if (exec) {
322     gatt_send_queue_write_cancel(tcb, p_clcb, flag);
323     return true;
324   }
325   return false;
326 }
327 
328 /** Send prepare write */
gatt_send_prepare_write(tGATT_TCB & tcb,tGATT_CLCB * p_clcb)329 void gatt_send_prepare_write(tGATT_TCB& tcb, tGATT_CLCB* p_clcb) {
330   tGATT_VALUE* p_attr = (tGATT_VALUE*)p_clcb->p_attr_buf;
331   uint8_t type = p_clcb->op_subtype;
332 
333   VLOG(1) << __func__ << StringPrintf(" type=0x%x", type);
334   uint16_t to_send = p_attr->len - p_attr->offset;
335 
336   if (to_send > (tcb.payload_size -
337                  GATT_WRITE_LONG_HDR_SIZE)) /* 2 = uint16_t offset bytes  */
338     to_send = tcb.payload_size - GATT_WRITE_LONG_HDR_SIZE;
339 
340   p_clcb->s_handle = p_attr->handle;
341 
342   uint16_t offset = p_attr->offset;
343   if (type == GATT_WRITE_PREPARE) {
344     offset += p_clcb->start_offset;
345   }
346 
347   VLOG(1) << StringPrintf("offset =0x%x len=%d", offset, to_send);
348 
349   uint8_t rt = gatt_send_write_msg(tcb, p_clcb, GATT_REQ_PREPARE_WRITE,
350                                    p_attr->handle, to_send, /* length */
351                                    offset,                  /* used as offset */
352                                    p_attr->value + p_attr->offset); /* data */
353 
354   /* remember the write long attribute length */
355   p_clcb->counter = to_send;
356 
357   if (rt != GATT_SUCCESS && rt != GATT_CMD_STARTED && rt != GATT_CONGESTED) {
358     gatt_end_operation(p_clcb, rt, NULL);
359   }
360 }
361 
362 /*******************************************************************************
363  *
364  * Function         gatt_process_find_type_value_rsp
365  *
366  * Description      This function handles the find by type value response.
367  *
368  *
369  * Returns          void
370  *
371  ******************************************************************************/
gatt_process_find_type_value_rsp(UNUSED_ATTR tGATT_TCB & tcb,tGATT_CLCB * p_clcb,uint16_t len,uint8_t * p_data)372 void gatt_process_find_type_value_rsp(UNUSED_ATTR tGATT_TCB& tcb,
373                                       tGATT_CLCB* p_clcb, uint16_t len,
374                                       uint8_t* p_data) {
375   tGATT_DISC_RES result;
376   uint8_t* p = p_data;
377 
378   VLOG(1) << __func__;
379   /* unexpected response */
380   if (p_clcb->operation != GATTC_OPTYPE_DISCOVERY ||
381       p_clcb->op_subtype != GATT_DISC_SRVC_BY_UUID)
382     return;
383 
384   memset(&result, 0, sizeof(tGATT_DISC_RES));
385   result.type = bluetooth::Uuid::From16Bit(GATT_UUID_PRI_SERVICE);
386 
387   /* returns a series of handle ranges */
388   while (len >= 4) {
389     STREAM_TO_UINT16(result.handle, p);
390     STREAM_TO_UINT16(result.value.group_value.e_handle, p);
391     result.value.group_value.service_type = p_clcb->uuid;
392 
393     len -= 4;
394 
395     if (p_clcb->p_reg->app_cb.p_disc_res_cb)
396       (*p_clcb->p_reg->app_cb.p_disc_res_cb)(p_clcb->conn_id,
397                                              p_clcb->op_subtype, &result);
398   }
399 
400   /* last handle  + 1 */
401   p_clcb->s_handle = (result.value.group_value.e_handle == 0)
402                          ? 0
403                          : (result.value.group_value.e_handle + 1);
404   /* initiate another request */
405   gatt_act_discovery(p_clcb);
406 }
407 /*******************************************************************************
408  *
409  * Function         gatt_process_read_info_rsp
410  *
411  * Description      This function is called to handle the read information
412  *                  response.
413  *
414  *
415  * Returns          void
416  *
417  ******************************************************************************/
gatt_process_read_info_rsp(UNUSED_ATTR tGATT_TCB & tcb,tGATT_CLCB * p_clcb,UNUSED_ATTR uint8_t op_code,uint16_t len,uint8_t * p_data)418 void gatt_process_read_info_rsp(UNUSED_ATTR tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
419                                 UNUSED_ATTR uint8_t op_code, uint16_t len,
420                                 uint8_t* p_data) {
421   tGATT_DISC_RES result;
422   uint8_t *p = p_data, uuid_len = 0, type;
423 
424   if (len < GATT_INFO_RSP_MIN_LEN) {
425     LOG(ERROR) << "invalid Info Response PDU received, discard.";
426     gatt_end_operation(p_clcb, GATT_INVALID_PDU, NULL);
427     return;
428   }
429   /* unexpected response */
430   if (p_clcb->operation != GATTC_OPTYPE_DISCOVERY ||
431       p_clcb->op_subtype != GATT_DISC_CHAR_DSCPT)
432     return;
433 
434   STREAM_TO_UINT8(type, p);
435   len -= 1;
436 
437   if (type == GATT_INFO_TYPE_PAIR_16)
438     uuid_len = Uuid::kNumBytes16;
439   else if (type == GATT_INFO_TYPE_PAIR_128)
440     uuid_len = Uuid::kNumBytes128;
441 
442   while (len >= uuid_len + 2) {
443     STREAM_TO_UINT16(result.handle, p);
444 
445     if (uuid_len > 0) {
446       if (!gatt_parse_uuid_from_cmd(&result.type, uuid_len, &p)) break;
447     } else
448       result.type = p_clcb->uuid;
449 
450     len -= (uuid_len + 2);
451 
452     if (p_clcb->p_reg->app_cb.p_disc_res_cb)
453       (*p_clcb->p_reg->app_cb.p_disc_res_cb)(p_clcb->conn_id,
454                                              p_clcb->op_subtype, &result);
455   }
456 
457   p_clcb->s_handle = (result.handle == 0) ? 0 : (result.handle + 1);
458   /* initiate another request */
459   gatt_act_discovery(p_clcb);
460 }
461 /*******************************************************************************
462  *
463  * Function         gatt_proc_disc_error_rsp
464  *
465  * Description      Process the read by type response and send another request
466  *                  if needed.
467  *
468  * Returns          void.
469  *
470  ******************************************************************************/
gatt_proc_disc_error_rsp(UNUSED_ATTR tGATT_TCB & tcb,tGATT_CLCB * p_clcb,uint8_t opcode,UNUSED_ATTR uint16_t handle,uint8_t reason)471 void gatt_proc_disc_error_rsp(UNUSED_ATTR tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
472                               uint8_t opcode, UNUSED_ATTR uint16_t handle,
473                               uint8_t reason) {
474   tGATT_STATUS status = (tGATT_STATUS)reason;
475 
476   VLOG(1) << __func__
477           << StringPrintf("reason: %02x cmd_code %04x", reason, opcode);
478 
479   switch (opcode) {
480     case GATT_REQ_READ_BY_GRP_TYPE:
481     case GATT_REQ_FIND_TYPE_VALUE:
482     case GATT_REQ_READ_BY_TYPE:
483     case GATT_REQ_FIND_INFO:
484       if (reason == GATT_NOT_FOUND) {
485         status = GATT_SUCCESS;
486         VLOG(1) << "Discovery completed";
487       }
488       break;
489     default:
490       LOG(ERROR) << StringPrintf("Incorrect discovery opcode %04x", opcode);
491       break;
492   }
493 
494   gatt_end_operation(p_clcb, status, NULL);
495 }
496 
497 /*******************************************************************************
498  *
499  * Function         gatt_process_error_rsp
500  *
501  * Description      This function is called to handle the error response
502  *
503  *
504  * Returns          void
505  *
506  ******************************************************************************/
gatt_process_error_rsp(tGATT_TCB & tcb,tGATT_CLCB * p_clcb,UNUSED_ATTR uint8_t op_code,UNUSED_ATTR uint16_t len,uint8_t * p_data)507 void gatt_process_error_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
508                             UNUSED_ATTR uint8_t op_code,
509                             UNUSED_ATTR uint16_t len, uint8_t* p_data) {
510   uint8_t opcode, reason, *p = p_data;
511   uint16_t handle;
512   tGATT_VALUE* p_attr = (tGATT_VALUE*)p_clcb->p_attr_buf;
513 
514   VLOG(1) << __func__;
515 
516   if (len < 4) {
517     android_errorWriteLog(0x534e4554, "79591688");
518     LOG(ERROR) << "Error response too short";
519     // Specification does not clearly define what should happen if error
520     // response is too short. General rule in BT Spec 5.0 Vol 3, Part F 3.4.1.1
521     // is: "If an error code is received in the Error Response that is not
522     // understood by the client, for example an error code that was reserved for
523     // future use that is now being used in a future version of this
524     // specification, then the Error Response shall still be considered to state
525     // that the given request cannot be performed for an unknown reason."
526     opcode = handle = 0;
527     reason = 0x7F;
528   } else {
529     STREAM_TO_UINT8(opcode, p);
530     STREAM_TO_UINT16(handle, p);
531     STREAM_TO_UINT8(reason, p);
532   }
533 
534   if (p_clcb->operation == GATTC_OPTYPE_DISCOVERY) {
535     gatt_proc_disc_error_rsp(tcb, p_clcb, opcode, handle, reason);
536   } else {
537     if ((p_clcb->operation == GATTC_OPTYPE_WRITE) &&
538         (p_clcb->op_subtype == GATT_WRITE) &&
539         (opcode == GATT_REQ_PREPARE_WRITE) && (p_attr) &&
540         (handle == p_attr->handle)) {
541       p_clcb->status = reason;
542       gatt_send_queue_write_cancel(tcb, p_clcb, GATT_PREP_WRITE_CANCEL);
543     } else if ((p_clcb->operation == GATTC_OPTYPE_READ) &&
544                ((p_clcb->op_subtype == GATT_READ_CHAR_VALUE_HDL) ||
545                 (p_clcb->op_subtype == GATT_READ_BY_HANDLE)) &&
546                (opcode == GATT_REQ_READ_BLOB) &&
547                p_clcb->first_read_blob_after_read &&
548                (reason == GATT_NOT_LONG)) {
549       gatt_end_operation(p_clcb, GATT_SUCCESS, (void*)p_clcb->p_attr_buf);
550     } else
551       gatt_end_operation(p_clcb, reason, NULL);
552   }
553 }
554 /*******************************************************************************
555  *
556  * Function         gatt_process_prep_write_rsp
557  *
558  * Description      This function is called to handle the read response
559  *
560  *
561  * Returns          void
562  *
563  ******************************************************************************/
gatt_process_prep_write_rsp(tGATT_TCB & tcb,tGATT_CLCB * p_clcb,uint8_t op_code,uint16_t len,uint8_t * p_data)564 void gatt_process_prep_write_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
565                                  uint8_t op_code, uint16_t len,
566                                  uint8_t* p_data) {
567   uint8_t* p = p_data;
568 
569   tGATT_VALUE value = {
570       .conn_id = p_clcb->conn_id, .auth_req = GATT_AUTH_REQ_NONE,
571   };
572 
573   LOG(ERROR) << StringPrintf("value resp op_code = %s len = %d",
574                              gatt_dbg_op_name(op_code), len);
575 
576   if (len < GATT_PREP_WRITE_RSP_MIN_LEN) {
577     LOG(ERROR) << "illegal prepare write response length, discard";
578     gatt_end_operation(p_clcb, GATT_INVALID_PDU, &value);
579     return;
580   }
581 
582   STREAM_TO_UINT16(value.handle, p);
583   STREAM_TO_UINT16(value.offset, p);
584 
585   value.len = len - 4;
586 
587   memcpy(value.value, p, value.len);
588 
589   if (p_clcb->op_subtype == GATT_WRITE_PREPARE) {
590     p_clcb->status = GATT_SUCCESS;
591     /* application should verify handle offset
592        and value are matched or not */
593 
594     gatt_end_operation(p_clcb, p_clcb->status, &value);
595   } else if (p_clcb->op_subtype == GATT_WRITE) {
596     if (!gatt_check_write_long_terminate(tcb, p_clcb, &value))
597       gatt_send_prepare_write(tcb, p_clcb);
598   }
599 }
600 /*******************************************************************************
601  *
602  * Function         gatt_process_notification
603  *
604  * Description      Handle the handle value indication/notification.
605  *
606  * Returns          void
607  *
608  ******************************************************************************/
gatt_process_notification(tGATT_TCB & tcb,uint8_t op_code,uint16_t len,uint8_t * p_data)609 void gatt_process_notification(tGATT_TCB& tcb, uint8_t op_code, uint16_t len,
610                                uint8_t* p_data) {
611   tGATT_VALUE value;
612   tGATT_REG* p_reg;
613   uint16_t conn_id;
614   tGATT_STATUS encrypt_status;
615   uint8_t* p = p_data;
616   uint8_t i;
617   uint8_t event = (op_code == GATT_HANDLE_VALUE_NOTIF)
618                       ? GATTC_OPTYPE_NOTIFICATION
619                       : GATTC_OPTYPE_INDICATION;
620 
621   VLOG(1) << __func__;
622 
623   if (len < GATT_NOTIFICATION_MIN_LEN) {
624     LOG(ERROR) << "illegal notification PDU length, discard";
625     return;
626   }
627 
628   memset(&value, 0, sizeof(value));
629   STREAM_TO_UINT16(value.handle, p);
630   value.len = len - 2;
631   memcpy(value.value, p, value.len);
632 
633   if (!GATT_HANDLE_IS_VALID(value.handle)) {
634     /* illegal handle, send ack now */
635     if (op_code == GATT_HANDLE_VALUE_IND)
636       attp_send_cl_msg(tcb, nullptr, GATT_HANDLE_VALUE_CONF, NULL);
637     return;
638   }
639 
640   if (event == GATTC_OPTYPE_INDICATION) {
641     if (tcb.ind_count) {
642       /* this is an error case that receiving an indication but we
643          still has an indication not being acked yet.
644          For now, just log the error reset the counter.
645          Later we need to disconnect the link unconditionally.
646       */
647       LOG(ERROR) << __func__ << " rcv Ind. but ind_count=" << tcb.ind_count
648                  << " (will reset ind_count)";
649     }
650     tcb.ind_count = 0;
651   }
652 
653   /* should notify all registered client with the handle value
654      notificaion/indication
655      Note: need to do the indication count and start timer first then do
656      callback
657    */
658 
659   for (i = 0, p_reg = gatt_cb.cl_rcb; i < GATT_MAX_APPS; i++, p_reg++) {
660     if (p_reg->in_use && p_reg->app_cb.p_cmpl_cb &&
661         (event == GATTC_OPTYPE_INDICATION))
662       tcb.ind_count++;
663   }
664 
665   if (event == GATTC_OPTYPE_INDICATION) {
666     /* start a timer for app confirmation */
667     if (tcb.ind_count > 0)
668       gatt_start_ind_ack_timer(tcb);
669     else /* no app to indicate, or invalid handle */
670       attp_send_cl_msg(tcb, nullptr, GATT_HANDLE_VALUE_CONF, NULL);
671   }
672 
673   encrypt_status = gatt_get_link_encrypt_status(tcb);
674   tGATT_CL_COMPLETE gatt_cl_complete;
675   gatt_cl_complete.att_value = value;
676   for (i = 0, p_reg = gatt_cb.cl_rcb; i < GATT_MAX_APPS; i++, p_reg++) {
677     if (p_reg->in_use && p_reg->app_cb.p_cmpl_cb) {
678       conn_id = GATT_CREATE_CONN_ID(tcb.tcb_idx, p_reg->gatt_if);
679       (*p_reg->app_cb.p_cmpl_cb)(conn_id, event, encrypt_status,
680                                  &gatt_cl_complete);
681     }
682   }
683 }
684 
685 /*******************************************************************************
686  *
687  * Function         gatt_process_read_by_type_rsp
688  *
689  * Description      This function is called to handle the read by type response.
690  *                  read by type can be used for discovery, or read by type or
691  *                  read characteristic value.
692  *
693  * Returns          void
694  *
695  ******************************************************************************/
gatt_process_read_by_type_rsp(tGATT_TCB & tcb,tGATT_CLCB * p_clcb,uint8_t op_code,uint16_t len,uint8_t * p_data)696 void gatt_process_read_by_type_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
697                                    uint8_t op_code, uint16_t len,
698                                    uint8_t* p_data) {
699   tGATT_DISC_RES result;
700   tGATT_DISC_VALUE record_value;
701   uint8_t *p = p_data, value_len, handle_len = 2;
702   uint16_t handle = 0;
703 
704   /* discovery procedure and no callback function registered */
705   if (((!p_clcb->p_reg) || (!p_clcb->p_reg->app_cb.p_disc_res_cb)) &&
706       (p_clcb->operation == GATTC_OPTYPE_DISCOVERY))
707     return;
708 
709   if (len < GATT_READ_BY_TYPE_RSP_MIN_LEN) {
710     LOG(ERROR) << "Illegal ReadByType/ReadByGroupType Response length, discard";
711     gatt_end_operation(p_clcb, GATT_INVALID_PDU, NULL);
712     return;
713   }
714 
715   STREAM_TO_UINT8(value_len, p);
716 
717   if ((value_len > (tcb.payload_size - 2)) || (value_len > (len - 1))) {
718     /* this is an error case that server's response containing a value length
719        which is larger than MTU-2
720        or value_len > message total length -1 */
721     LOG(ERROR) << __func__
722                << StringPrintf(
723                       ": Discard response op_code=%d "
724                       "vale_len=%d > (MTU-2=%d or msg_len-1=%d)",
725                       op_code, value_len, (tcb.payload_size - 2), (len - 1));
726     gatt_end_operation(p_clcb, GATT_ERROR, NULL);
727     return;
728   }
729 
730   if (op_code == GATT_RSP_READ_BY_GRP_TYPE) handle_len = 4;
731 
732   value_len -= handle_len; /* substract the handle pairs bytes */
733   len -= 1;
734 
735   while (len >= (handle_len + value_len)) {
736     STREAM_TO_UINT16(handle, p);
737 
738     if (!GATT_HANDLE_IS_VALID(handle)) {
739       gatt_end_operation(p_clcb, GATT_INVALID_HANDLE, NULL);
740       return;
741     }
742 
743     memset(&result, 0, sizeof(tGATT_DISC_RES));
744     memset(&record_value, 0, sizeof(tGATT_DISC_VALUE));
745 
746     result.handle = handle;
747     result.type =
748         bluetooth::Uuid::From16Bit(disc_type_to_uuid[p_clcb->op_subtype]);
749 
750     /* discover all services */
751     if (p_clcb->operation == GATTC_OPTYPE_DISCOVERY &&
752         p_clcb->op_subtype == GATT_DISC_SRVC_ALL &&
753         op_code == GATT_RSP_READ_BY_GRP_TYPE) {
754       STREAM_TO_UINT16(handle, p);
755 
756       if (!GATT_HANDLE_IS_VALID(handle)) {
757         gatt_end_operation(p_clcb, GATT_INVALID_HANDLE, NULL);
758         return;
759       } else {
760         record_value.group_value.e_handle = handle;
761         if (!gatt_parse_uuid_from_cmd(&record_value.group_value.service_type,
762                                       value_len, &p)) {
763           LOG(ERROR) << "discover all service response parsing failure";
764           break;
765         }
766       }
767     }
768     /* discover included service */
769     else if (p_clcb->operation == GATTC_OPTYPE_DISCOVERY &&
770              p_clcb->op_subtype == GATT_DISC_INC_SRVC) {
771       if (value_len < 4) {
772         android_errorWriteLog(0x534e4554, "158833854");
773         LOG(ERROR) << __func__ << " Illegal Response length, must be at least 4.";
774         gatt_end_operation(p_clcb, GATT_INVALID_PDU, NULL);
775         return;
776       }
777       STREAM_TO_UINT16(record_value.incl_service.s_handle, p);
778       STREAM_TO_UINT16(record_value.incl_service.e_handle, p);
779 
780       if (!GATT_HANDLE_IS_VALID(record_value.incl_service.s_handle) ||
781           !GATT_HANDLE_IS_VALID(record_value.incl_service.e_handle)) {
782         gatt_end_operation(p_clcb, GATT_INVALID_HANDLE, NULL);
783         return;
784       }
785 
786       if (value_len == 6) {
787         uint16_t tmp;
788         STREAM_TO_UINT16(tmp, p);
789         record_value.incl_service.service_type =
790             bluetooth::Uuid::From16Bit(tmp);
791       } else if (value_len == 4) {
792         p_clcb->s_handle = record_value.incl_service.s_handle;
793         p_clcb->read_uuid128.wait_for_read_rsp = true;
794         p_clcb->read_uuid128.next_disc_start_hdl = handle + 1;
795         memcpy(&p_clcb->read_uuid128.result, &result, sizeof(result));
796         memcpy(&p_clcb->read_uuid128.result.value, &record_value,
797                sizeof(result.value));
798         p_clcb->op_subtype |= 0x90;
799         gatt_act_read(p_clcb, 0);
800         return;
801       } else {
802         LOG(ERROR) << __func__
803                    << ": INCL_SRVC failed with invalid data value_len="
804                    << +value_len;
805         gatt_end_operation(p_clcb, GATT_INVALID_PDU, (void*)p);
806         return;
807       }
808     }
809     /* read by type */
810     else if (p_clcb->operation == GATTC_OPTYPE_READ &&
811              p_clcb->op_subtype == GATT_READ_BY_TYPE) {
812       p_clcb->counter = len - 2;
813       p_clcb->s_handle = handle;
814       if (p_clcb->counter == (p_clcb->p_tcb->payload_size - 4)) {
815         p_clcb->op_subtype = GATT_READ_BY_HANDLE;
816         if (!p_clcb->p_attr_buf)
817           p_clcb->p_attr_buf = (uint8_t*)osi_malloc(GATT_MAX_ATTR_LEN);
818         if (p_clcb->counter <= GATT_MAX_ATTR_LEN) {
819           memcpy(p_clcb->p_attr_buf, p, p_clcb->counter);
820           gatt_act_read(p_clcb, p_clcb->counter);
821         } else {
822           gatt_end_operation(p_clcb, GATT_INTERNAL_ERROR, (void*)p);
823         }
824       } else {
825         gatt_end_operation(p_clcb, GATT_SUCCESS, (void*)p);
826       }
827       return;
828     } else /* discover characterisitic */
829     {
830       if (value_len < 3) {
831         android_errorWriteLog(0x534e4554, "158778659");
832         LOG(ERROR) << __func__ << " Illegal Response length, must be at least 3.";
833         gatt_end_operation(p_clcb, GATT_INVALID_PDU, NULL);
834         return;
835       }
836       STREAM_TO_UINT8(record_value.dclr_value.char_prop, p);
837       STREAM_TO_UINT16(record_value.dclr_value.val_handle, p);
838       if (!GATT_HANDLE_IS_VALID(record_value.dclr_value.val_handle)) {
839         gatt_end_operation(p_clcb, GATT_INVALID_HANDLE, NULL);
840         return;
841       }
842       if (!gatt_parse_uuid_from_cmd(&record_value.dclr_value.char_uuid,
843                                     (uint16_t)(value_len - 3), &p)) {
844         gatt_end_operation(p_clcb, GATT_SUCCESS, NULL);
845         /* invalid format, and skip the result */
846         return;
847       }
848 
849       /* UUID not matching */
850       if (!p_clcb->uuid.IsEmpty() &&
851           !record_value.dclr_value.char_uuid.IsEmpty() &&
852           record_value.dclr_value.char_uuid != p_clcb->uuid) {
853         len -= (value_len + 2);
854         continue; /* skip the result, and look for next one */
855       }
856 
857       if (p_clcb->operation == GATTC_OPTYPE_READ)
858       /* UUID match for read characteristic value */
859       {
860         /* only read the first matching UUID characteristic value, and
861           discard the rest results */
862         p_clcb->s_handle = record_value.dclr_value.val_handle;
863         p_clcb->op_subtype |= 0x80;
864         gatt_act_read(p_clcb, 0);
865         return;
866       }
867     }
868     len -= (value_len + handle_len);
869 
870     /* result is (handle, 16bits UUID) pairs */
871     memcpy(&result.value, &record_value, sizeof(result.value));
872 
873     /* send callback if is discover procedure */
874     if (p_clcb->operation == GATTC_OPTYPE_DISCOVERY &&
875         p_clcb->p_reg->app_cb.p_disc_res_cb)
876       (*p_clcb->p_reg->app_cb.p_disc_res_cb)(p_clcb->conn_id,
877                                              p_clcb->op_subtype, &result);
878   }
879 
880   p_clcb->s_handle = (handle == 0) ? 0 : (handle + 1);
881 
882   if (p_clcb->operation == GATTC_OPTYPE_DISCOVERY) {
883     /* initiate another request */
884     gatt_act_discovery(p_clcb);
885   } else /* read characteristic value */
886   {
887     gatt_act_read(p_clcb, 0);
888   }
889 }
890 
891 /*******************************************************************************
892  *
893  * Function         gatt_process_read_rsp
894  *
895  * Description      This function is called to handle the read BLOB response
896  *
897  *
898  * Returns          void
899  *
900  ******************************************************************************/
gatt_process_read_rsp(tGATT_TCB & tcb,tGATT_CLCB * p_clcb,UNUSED_ATTR uint8_t op_code,uint16_t len,uint8_t * p_data)901 void gatt_process_read_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
902                            UNUSED_ATTR uint8_t op_code, uint16_t len,
903                            uint8_t* p_data) {
904   uint16_t offset = p_clcb->counter;
905   uint8_t* p = p_data;
906 
907   if (p_clcb->operation == GATTC_OPTYPE_READ) {
908     if (p_clcb->op_subtype != GATT_READ_BY_HANDLE) {
909       p_clcb->counter = len;
910       gatt_end_operation(p_clcb, GATT_SUCCESS, (void*)p);
911     } else {
912       /* allocate GKI buffer holding up long attribute value  */
913       if (!p_clcb->p_attr_buf)
914         p_clcb->p_attr_buf = (uint8_t*)osi_malloc(GATT_MAX_ATTR_LEN);
915 
916       /* copy attrobute value into cb buffer  */
917       if (offset < GATT_MAX_ATTR_LEN) {
918         if ((len + offset) > GATT_MAX_ATTR_LEN)
919           len = GATT_MAX_ATTR_LEN - offset;
920 
921         p_clcb->counter += len;
922 
923         memcpy(p_clcb->p_attr_buf + offset, p, len);
924 
925         /* send next request if needed  */
926 
927         if (len == (tcb.payload_size -
928                     1) && /* full packet for read or read blob rsp */
929             len + offset < GATT_MAX_ATTR_LEN) {
930           VLOG(1) << StringPrintf(
931               "full pkt issue read blob for remianing bytes old offset=%d "
932               "len=%d new offset=%d",
933               offset, len, p_clcb->counter);
934           gatt_act_read(p_clcb, p_clcb->counter);
935         } else /* end of request, send callback */
936         {
937           gatt_end_operation(p_clcb, GATT_SUCCESS, (void*)p_clcb->p_attr_buf);
938         }
939       } else /* exception, should not happen */
940       {
941         LOG(ERROR) << "attr offset = " << +offset
942                    << " p_attr_buf = " << p_clcb->p_attr_buf;
943         gatt_end_operation(p_clcb, GATT_NO_RESOURCES,
944                            (void*)p_clcb->p_attr_buf);
945       }
946     }
947   } else {
948     if (p_clcb->operation == GATTC_OPTYPE_DISCOVERY &&
949         p_clcb->op_subtype == GATT_DISC_INC_SRVC &&
950         p_clcb->read_uuid128.wait_for_read_rsp) {
951       p_clcb->s_handle = p_clcb->read_uuid128.next_disc_start_hdl;
952       p_clcb->read_uuid128.wait_for_read_rsp = false;
953       if (len == Uuid::kNumBytes128) {
954         p_clcb->read_uuid128.result.value.incl_service.service_type =
955             bluetooth::Uuid::From128BitLE(p);
956         if (p_clcb->p_reg->app_cb.p_disc_res_cb)
957           (*p_clcb->p_reg->app_cb.p_disc_res_cb)(p_clcb->conn_id,
958                                                  p_clcb->op_subtype,
959                                                  &p_clcb->read_uuid128.result);
960         gatt_act_discovery(p_clcb);
961       } else {
962         gatt_end_operation(p_clcb, GATT_INVALID_PDU, (void*)p);
963       }
964     }
965   }
966 }
967 
968 /*******************************************************************************
969  *
970  * Function         gatt_process_handle_rsp
971  *
972  * Description      This function is called to handle the write response
973  *
974  *
975  * Returns          void
976  *
977  ******************************************************************************/
gatt_process_handle_rsp(tGATT_CLCB * p_clcb)978 void gatt_process_handle_rsp(tGATT_CLCB* p_clcb) {
979   gatt_end_operation(p_clcb, GATT_SUCCESS, NULL);
980 }
981 /*******************************************************************************
982  *
983  * Function         gatt_process_mtu_rsp
984  *
985  * Description      Process the configure MTU response.
986  *
987  *
988  * Returns          void
989  *
990  ******************************************************************************/
gatt_process_mtu_rsp(tGATT_TCB & tcb,tGATT_CLCB * p_clcb,uint16_t len,uint8_t * p_data)991 void gatt_process_mtu_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb, uint16_t len,
992                           uint8_t* p_data) {
993   uint16_t mtu;
994   tGATT_STATUS status = GATT_SUCCESS;
995 
996   if (len < GATT_MTU_RSP_MIN_LEN) {
997     LOG(ERROR) << "invalid MTU response PDU received, discard.";
998     status = GATT_INVALID_PDU;
999   } else {
1000     STREAM_TO_UINT16(mtu, p_data);
1001 
1002     if (mtu < tcb.payload_size && mtu >= GATT_DEF_BLE_MTU_SIZE)
1003       tcb.payload_size = mtu;
1004   }
1005 
1006   l2cble_set_fixed_channel_tx_data_length(tcb.peer_bda, L2CAP_ATT_CID,
1007                                           tcb.payload_size);
1008   gatt_end_operation(p_clcb, status, NULL);
1009 }
1010 /*******************************************************************************
1011  *
1012  * Function         gatt_cmd_to_rsp_code
1013  *
1014  * Description      Convert an ATT command op code into the corresponding
1015  *                  response code assume no error occurs.
1016  *
1017  * Returns          response code.
1018  *
1019  ******************************************************************************/
gatt_cmd_to_rsp_code(uint8_t cmd_code)1020 uint8_t gatt_cmd_to_rsp_code(uint8_t cmd_code) {
1021   uint8_t rsp_code = 0;
1022 
1023   if (cmd_code > 1 && cmd_code != GATT_CMD_WRITE) {
1024     rsp_code = cmd_code + 1;
1025   }
1026   return rsp_code;
1027 }
1028 
1029 /** Find next command in queue and sent to server */
gatt_cl_send_next_cmd_inq(tGATT_TCB & tcb)1030 bool gatt_cl_send_next_cmd_inq(tGATT_TCB& tcb) {
1031   while (!tcb.cl_cmd_q.empty()) {
1032     tGATT_CMD_Q& cmd = tcb.cl_cmd_q.front();
1033     if (!cmd.to_send || cmd.p_cmd == NULL) return false;
1034 
1035     tGATT_STATUS att_ret = attp_send_msg_to_l2cap(tcb, cmd.p_cmd);
1036     if (att_ret != GATT_SUCCESS && att_ret != GATT_CONGESTED) {
1037       LOG(ERROR) << __func__ << ": L2CAP sent error";
1038       tcb.cl_cmd_q.pop();
1039       continue;
1040     }
1041 
1042     cmd.to_send = false;
1043     cmd.p_cmd = NULL;
1044 
1045     if (cmd.op_code == GATT_CMD_WRITE || cmd.op_code == GATT_SIGN_CMD_WRITE) {
1046       /* dequeue the request if is write command or sign write */
1047       uint8_t rsp_code;
1048       tGATT_CLCB* p_clcb = gatt_cmd_dequeue(tcb, &rsp_code);
1049 
1050       /* send command complete callback here */
1051       gatt_end_operation(p_clcb, att_ret, NULL);
1052 
1053       /* if no ack needed, keep sending */
1054       if (att_ret == GATT_SUCCESS) continue;
1055 
1056       return true;
1057     }
1058 
1059     gatt_start_rsp_timer(cmd.p_clcb);
1060     return true;
1061   }
1062 
1063   return false;
1064 }
1065 
1066 /** This function is called to handle the server response to client */
gatt_client_handle_server_rsp(tGATT_TCB & tcb,uint8_t op_code,uint16_t len,uint8_t * p_data)1067 void gatt_client_handle_server_rsp(tGATT_TCB& tcb, uint8_t op_code,
1068                                    uint16_t len, uint8_t* p_data) {
1069   if (op_code == GATT_HANDLE_VALUE_IND || op_code == GATT_HANDLE_VALUE_NOTIF) {
1070     if (len >= tcb.payload_size) {
1071       LOG(ERROR) << StringPrintf(
1072           "%s: invalid indicate pkt size: %d, PDU size: %d", __func__, len + 1,
1073           tcb.payload_size);
1074       return;
1075     }
1076 
1077     gatt_process_notification(tcb, op_code, len, p_data);
1078     return;
1079   }
1080 
1081   uint8_t cmd_code = 0;
1082   tGATT_CLCB* p_clcb = gatt_cmd_dequeue(tcb, &cmd_code);
1083   uint8_t rsp_code = gatt_cmd_to_rsp_code(cmd_code);
1084   if (!p_clcb || (rsp_code != op_code && op_code != GATT_RSP_ERROR)) {
1085     LOG(WARNING) << StringPrintf(
1086         "ATT - Ignore wrong response. Receives (%02x) Request(%02x) Ignored",
1087         op_code, rsp_code);
1088     return;
1089   }
1090 
1091   if (!p_clcb->in_use) {
1092     LOG(WARNING) << "ATT - clcb already not in use, ignoring response";
1093     gatt_cl_send_next_cmd_inq(tcb);
1094     return;
1095   }
1096 
1097   alarm_cancel(p_clcb->gatt_rsp_timer_ent);
1098   p_clcb->retry_count = 0;
1099 
1100   /* the size of the message may not be bigger than the local max PDU size*/
1101   /* The message has to be smaller than the agreed MTU, len does not count
1102    * op_code */
1103   if (len >= tcb.payload_size) {
1104     LOG(ERROR) << StringPrintf(
1105         "%s: invalid response pkt size: %d, PDU size: %d", __func__, len + 1,
1106         tcb.payload_size);
1107     gatt_end_operation(p_clcb, GATT_ERROR, NULL);
1108   } else {
1109     switch (op_code) {
1110       case GATT_RSP_ERROR:
1111         gatt_process_error_rsp(tcb, p_clcb, op_code, len, p_data);
1112         break;
1113 
1114       case GATT_RSP_MTU: /* 2 bytes mtu */
1115         gatt_process_mtu_rsp(tcb, p_clcb, len, p_data);
1116         break;
1117 
1118       case GATT_RSP_FIND_INFO:
1119         gatt_process_read_info_rsp(tcb, p_clcb, op_code, len, p_data);
1120         break;
1121 
1122       case GATT_RSP_READ_BY_TYPE:
1123       case GATT_RSP_READ_BY_GRP_TYPE:
1124         gatt_process_read_by_type_rsp(tcb, p_clcb, op_code, len, p_data);
1125         break;
1126 
1127       case GATT_RSP_READ:
1128       case GATT_RSP_READ_BLOB:
1129       case GATT_RSP_READ_MULTI:
1130         gatt_process_read_rsp(tcb, p_clcb, op_code, len, p_data);
1131         break;
1132 
1133       case GATT_RSP_FIND_TYPE_VALUE: /* disc service with UUID */
1134         gatt_process_find_type_value_rsp(tcb, p_clcb, len, p_data);
1135         break;
1136 
1137       case GATT_RSP_WRITE:
1138         gatt_process_handle_rsp(p_clcb);
1139         break;
1140 
1141       case GATT_RSP_PREPARE_WRITE:
1142         gatt_process_prep_write_rsp(tcb, p_clcb, op_code, len, p_data);
1143         break;
1144 
1145       case GATT_RSP_EXEC_WRITE:
1146         gatt_end_operation(p_clcb, p_clcb->status, NULL);
1147         break;
1148 
1149       default:
1150         LOG(ERROR) << __func__ << ": Unknown opcode = " << std::hex << op_code;
1151         break;
1152     }
1153   }
1154 
1155   gatt_cl_send_next_cmd_inq(tcb);
1156 }
1157