• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /******************************************************************************
2  *
3  *  Copyright (C) 2006-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 action functions for BTA JV APIs.
22  *
23  ******************************************************************************/
24 #include <arpa/inet.h>
25 #include <hardware/bluetooth.h>
26 #include <pthread.h>
27 #include <stdlib.h>
28 #include <string.h>
29 
30 #include "avct_api.h"
31 #include "avdt_api.h"
32 #include "bt_common.h"
33 #include "bt_types.h"
34 #include "bta_api.h"
35 #include "bta_jv_api.h"
36 #include "bta_jv_co.h"
37 #include "bta_jv_int.h"
38 #include "bta_sys.h"
39 #include "btm_api.h"
40 #include "btm_int.h"
41 #include "gap_api.h"
42 #include "l2c_api.h"
43 #include "osi/include/allocator.h"
44 #include "port_api.h"
45 #include "rfcdefs.h"
46 #include "sdp_api.h"
47 #include "utl.h"
48 
49 #include "osi/include/osi.h"
50 
51 /* one of these exists for each client */
52 struct fc_client {
53   struct fc_client* next_all_list;
54   struct fc_client* next_chan_list;
55   RawAddress remote_addr;
56   uint32_t id;
57   tBTA_JV_L2CAP_CBACK* p_cback;
58   uint32_t l2cap_socket_id;
59   uint16_t handle;
60   uint16_t chan;
61   uint8_t sec_id;
62   unsigned server : 1;
63   unsigned init_called : 1;
64 };
65 
66 /* one of these exists for each channel we're dealing with */
67 struct fc_channel {
68   struct fc_channel* next;
69   struct fc_client* clients;
70   uint8_t has_server : 1;
71   uint16_t chan;
72 };
73 
74 static struct fc_client* fc_clients;
75 static struct fc_channel* fc_channels;
76 static uint32_t fc_next_id;
77 
78 static void fcchan_conn_chng_cbk(uint16_t chan, const RawAddress& bd_addr,
79                                  bool connected, uint16_t reason,
80                                  tBT_TRANSPORT);
81 static void fcchan_data_cbk(uint16_t chan, const RawAddress& bd_addr,
82                             BT_HDR* p_buf);
83 
84 extern void uuid_to_string_legacy(bt_uuid_t* p_uuid, char* str, size_t str_len);
logu(const char * title,const uint8_t * p_uuid)85 static inline void logu(const char* title, const uint8_t* p_uuid) {
86   char uuids[128];
87   uuid_to_string_legacy((bt_uuid_t*)p_uuid, uuids, sizeof(uuids));
88   APPL_TRACE_DEBUG("%s: %s", title, uuids);
89 }
90 
91 static tBTA_JV_PCB* bta_jv_add_rfc_port(tBTA_JV_RFC_CB* p_cb,
92                                         tBTA_JV_PCB* p_pcb_open);
93 static tBTA_JV_STATUS bta_jv_free_set_pm_profile_cb(uint32_t jv_handle);
94 static void bta_jv_pm_conn_busy(tBTA_JV_PM_CB* p_cb);
95 static void bta_jv_pm_conn_idle(tBTA_JV_PM_CB* p_cb);
96 static void bta_jv_pm_state_change(tBTA_JV_PM_CB* p_cb,
97                                    const tBTA_JV_CONN_STATE state);
98 tBTA_JV_STATUS bta_jv_set_pm_conn_state(tBTA_JV_PM_CB* p_cb,
99                                         const tBTA_JV_CONN_STATE new_st);
100 
101 /*******************************************************************************
102  *
103  * Function     bta_jv_alloc_sec_id
104  *
105  * Description  allocate a security id
106  *
107  * Returns
108  *
109  ******************************************************************************/
bta_jv_alloc_sec_id(void)110 uint8_t bta_jv_alloc_sec_id(void) {
111   uint8_t ret = 0;
112   int i;
113   for (i = 0; i < BTA_JV_NUM_SERVICE_ID; i++) {
114     if (0 == bta_jv_cb.sec_id[i]) {
115       bta_jv_cb.sec_id[i] = BTA_JV_FIRST_SERVICE_ID + i;
116       ret = bta_jv_cb.sec_id[i];
117       break;
118     }
119   }
120   return ret;
121 }
get_sec_id_used(void)122 static int get_sec_id_used(void) {
123   int i;
124   int used = 0;
125   for (i = 0; i < BTA_JV_NUM_SERVICE_ID; i++) {
126     if (bta_jv_cb.sec_id[i]) used++;
127   }
128   if (used == BTA_JV_NUM_SERVICE_ID)
129     APPL_TRACE_ERROR("get_sec_id_used, sec id exceeds the limit:%d",
130                      BTA_JV_NUM_SERVICE_ID);
131   return used;
132 }
get_rfc_cb_used(void)133 static int get_rfc_cb_used(void) {
134   int i;
135   int used = 0;
136   for (i = 0; i < BTA_JV_MAX_RFC_CONN; i++) {
137     if (bta_jv_cb.rfc_cb[i].handle) used++;
138   }
139   if (used == BTA_JV_MAX_RFC_CONN)
140     APPL_TRACE_ERROR("get_sec_id_used, rfc ctrl block exceeds the limit:%d",
141                      BTA_JV_MAX_RFC_CONN);
142   return used;
143 }
144 
145 /*******************************************************************************
146  *
147  * Function     bta_jv_free_sec_id
148  *
149  * Description  free the given security id
150  *
151  * Returns
152  *
153  ******************************************************************************/
bta_jv_free_sec_id(uint8_t * p_sec_id)154 static void bta_jv_free_sec_id(uint8_t* p_sec_id) {
155   uint8_t sec_id = *p_sec_id;
156   *p_sec_id = 0;
157   if (sec_id >= BTA_JV_FIRST_SERVICE_ID && sec_id <= BTA_JV_LAST_SERVICE_ID) {
158     BTM_SecClrService(sec_id);
159     bta_jv_cb.sec_id[sec_id - BTA_JV_FIRST_SERVICE_ID] = 0;
160   }
161 }
162 
163 /*******************************************************************************
164  *
165  * Function     bta_jv_alloc_rfc_cb
166  *
167  * Description  allocate a control block for the given port handle
168  *
169  * Returns
170  *
171  ******************************************************************************/
bta_jv_alloc_rfc_cb(uint16_t port_handle,tBTA_JV_PCB ** pp_pcb)172 tBTA_JV_RFC_CB* bta_jv_alloc_rfc_cb(uint16_t port_handle,
173                                     tBTA_JV_PCB** pp_pcb) {
174   tBTA_JV_RFC_CB* p_cb = NULL;
175   tBTA_JV_PCB* p_pcb;
176   int i, j;
177   for (i = 0; i < BTA_JV_MAX_RFC_CONN; i++) {
178     if (0 == bta_jv_cb.rfc_cb[i].handle) {
179       p_cb = &bta_jv_cb.rfc_cb[i];
180       /* mask handle to distinguish it with L2CAP handle */
181       p_cb->handle = (i + 1) | BTA_JV_RFCOMM_MASK;
182 
183       p_cb->max_sess = 1;
184       p_cb->curr_sess = 1;
185       for (j = 0; j < BTA_JV_MAX_RFC_SR_SESSION; j++) p_cb->rfc_hdl[j] = 0;
186       p_cb->rfc_hdl[0] = port_handle;
187       APPL_TRACE_DEBUG("bta_jv_alloc_rfc_cb port_handle:%d handle:0x%2x",
188                        port_handle, p_cb->handle);
189 
190       p_pcb = &bta_jv_cb.port_cb[port_handle - 1];
191       p_pcb->handle = p_cb->handle;
192       p_pcb->port_handle = port_handle;
193       p_pcb->p_pm_cb = NULL;
194       *pp_pcb = p_pcb;
195       break;
196     }
197   }
198   if (p_cb == NULL) {
199     APPL_TRACE_ERROR(
200         "bta_jv_alloc_rfc_cb: port_handle:%d, ctrl block exceeds "
201         "limit:%d",
202         port_handle, BTA_JV_MAX_RFC_CONN);
203   }
204   return p_cb;
205 }
206 
207 /*******************************************************************************
208  *
209  * Function     bta_jv_rfc_port_to_pcb
210  *
211  * Description  find the port control block associated with the given port
212  *              handle
213  *
214  * Returns
215  *
216  ******************************************************************************/
bta_jv_rfc_port_to_pcb(uint16_t port_handle)217 tBTA_JV_PCB* bta_jv_rfc_port_to_pcb(uint16_t port_handle) {
218   tBTA_JV_PCB* p_pcb = NULL;
219 
220   if ((port_handle > 0) && (port_handle <= MAX_RFC_PORTS) &&
221       bta_jv_cb.port_cb[port_handle - 1].handle) {
222     p_pcb = &bta_jv_cb.port_cb[port_handle - 1];
223   }
224 
225   return p_pcb;
226 }
227 
228 /*******************************************************************************
229  *
230  * Function     bta_jv_rfc_port_to_cb
231  *
232  * Description  find the RFCOMM control block associated with the given port
233  *              handle
234  *
235  * Returns
236  *
237  ******************************************************************************/
bta_jv_rfc_port_to_cb(uint16_t port_handle)238 tBTA_JV_RFC_CB* bta_jv_rfc_port_to_cb(uint16_t port_handle) {
239   tBTA_JV_RFC_CB* p_cb = NULL;
240   uint32_t handle;
241 
242   if ((port_handle > 0) && (port_handle <= MAX_RFC_PORTS) &&
243       bta_jv_cb.port_cb[port_handle - 1].handle) {
244     handle = bta_jv_cb.port_cb[port_handle - 1].handle;
245     handle &= BTA_JV_RFC_HDL_MASK;
246     handle &= ~BTA_JV_RFCOMM_MASK;
247     if (handle) p_cb = &bta_jv_cb.rfc_cb[handle - 1];
248   } else {
249     APPL_TRACE_WARNING(
250         "bta_jv_rfc_port_to_cb(port_handle:0x%x):jv handle:0x%x not"
251         " FOUND",
252         port_handle, bta_jv_cb.port_cb[port_handle - 1].handle);
253   }
254   return p_cb;
255 }
256 
bta_jv_free_rfc_cb(tBTA_JV_RFC_CB * p_cb,tBTA_JV_PCB * p_pcb)257 static tBTA_JV_STATUS bta_jv_free_rfc_cb(tBTA_JV_RFC_CB* p_cb,
258                                          tBTA_JV_PCB* p_pcb) {
259   tBTA_JV_STATUS status = BTA_JV_SUCCESS;
260   bool remove_server = false;
261   int close_pending = 0;
262 
263   if (!p_cb || !p_pcb) {
264     APPL_TRACE_ERROR("bta_jv_free_sr_rfc_cb, p_cb or p_pcb cannot be null");
265     return BTA_JV_FAILURE;
266   }
267   APPL_TRACE_DEBUG(
268       "bta_jv_free_sr_rfc_cb: max_sess:%d, curr_sess:%d, p_pcb:%p, user:"
269       "%p, state:%d, jv handle: 0x%x",
270       p_cb->max_sess, p_cb->curr_sess, p_pcb, p_pcb->rfcomm_slot_id,
271       p_pcb->state, p_pcb->handle);
272 
273   if (p_cb->curr_sess <= 0) return BTA_JV_SUCCESS;
274 
275   switch (p_pcb->state) {
276     case BTA_JV_ST_CL_CLOSING:
277     case BTA_JV_ST_SR_CLOSING:
278       APPL_TRACE_WARNING(
279           "bta_jv_free_sr_rfc_cb: return on closing, port state:%d, "
280           "scn:%d, p_pcb:%p, user_data:%p",
281           p_pcb->state, p_cb->scn, p_pcb, p_pcb->rfcomm_slot_id);
282       status = BTA_JV_FAILURE;
283       return status;
284     case BTA_JV_ST_CL_OPEN:
285     case BTA_JV_ST_CL_OPENING:
286       APPL_TRACE_DEBUG(
287           "bta_jv_free_sr_rfc_cb: state: %d, scn:%d,"
288           " user_data:%p",
289           p_pcb->state, p_cb->scn, p_pcb->rfcomm_slot_id);
290       p_pcb->state = BTA_JV_ST_CL_CLOSING;
291       break;
292     case BTA_JV_ST_SR_LISTEN:
293       p_pcb->state = BTA_JV_ST_SR_CLOSING;
294       remove_server = true;
295       APPL_TRACE_DEBUG(
296           "bta_jv_free_sr_rfc_cb: state: BTA_JV_ST_SR_LISTEN, scn:%d,"
297           " user_data:%p",
298           p_cb->scn, p_pcb->rfcomm_slot_id);
299       break;
300     case BTA_JV_ST_SR_OPEN:
301       p_pcb->state = BTA_JV_ST_SR_CLOSING;
302       APPL_TRACE_DEBUG(
303           "bta_jv_free_sr_rfc_cb: state: BTA_JV_ST_SR_OPEN, scn:%d,"
304           " user_data:%p",
305           p_cb->scn, p_pcb->rfcomm_slot_id);
306       break;
307     default:
308       APPL_TRACE_WARNING(
309           "bta_jv_free_sr_rfc_cb():failed, ignore port state:%d, scn:"
310           "%d, p_pcb:%p, jv handle: 0x%x, port_handle: %d, user_data:%p",
311           p_pcb->state, p_cb->scn, p_pcb, p_pcb->handle, p_pcb->port_handle,
312           p_pcb->rfcomm_slot_id);
313       status = BTA_JV_FAILURE;
314       break;
315   }
316   if (BTA_JV_SUCCESS == status) {
317     int port_status;
318 
319     if (!remove_server)
320       port_status = RFCOMM_RemoveConnection(p_pcb->port_handle);
321     else
322       port_status = RFCOMM_RemoveServer(p_pcb->port_handle);
323     if (port_status != PORT_SUCCESS) {
324       status = BTA_JV_FAILURE;
325       APPL_TRACE_WARNING(
326           "bta_jv_free_rfc_cb(jv handle: 0x%x, state %d)::"
327           "port_status: %d, port_handle: %d, close_pending: %d:Remove",
328           p_pcb->handle, p_pcb->state, port_status, p_pcb->port_handle,
329           close_pending);
330     }
331   }
332   if (!close_pending) {
333     p_pcb->port_handle = 0;
334     p_pcb->state = BTA_JV_ST_NONE;
335     bta_jv_free_set_pm_profile_cb(p_pcb->handle);
336 
337     // Initialize congestion flags
338     p_pcb->cong = false;
339     p_pcb->rfcomm_slot_id = 0;
340     int si = BTA_JV_RFC_HDL_TO_SIDX(p_pcb->handle);
341     if (0 <= si && si < BTA_JV_MAX_RFC_SR_SESSION) p_cb->rfc_hdl[si] = 0;
342     p_pcb->handle = 0;
343     p_cb->curr_sess--;
344     if (p_cb->curr_sess == 0) {
345       p_cb->scn = 0;
346       bta_jv_free_sec_id(&p_cb->sec_id);
347       p_cb->p_cback = NULL;
348       p_cb->handle = 0;
349       p_cb->curr_sess = -1;
350     }
351     if (remove_server) {
352       bta_jv_free_sec_id(&p_cb->sec_id);
353     }
354   }
355   return status;
356 }
357 
358 /*******************************************************************************
359  *
360  * Function     bta_jv_free_l2c_cb
361  *
362  * Description  free the given L2CAP control block
363  *
364  * Returns
365  *
366  ******************************************************************************/
bta_jv_free_l2c_cb(tBTA_JV_L2C_CB * p_cb)367 tBTA_JV_STATUS bta_jv_free_l2c_cb(tBTA_JV_L2C_CB* p_cb) {
368   tBTA_JV_STATUS status = BTA_JV_SUCCESS;
369 
370   if (BTA_JV_ST_NONE != p_cb->state) {
371     bta_jv_free_set_pm_profile_cb((uint32_t)p_cb->handle);
372     if (GAP_ConnClose(p_cb->handle) != BT_PASS) status = BTA_JV_FAILURE;
373   }
374   p_cb->psm = 0;
375   p_cb->state = BTA_JV_ST_NONE;
376   p_cb->cong = false;
377   bta_jv_free_sec_id(&p_cb->sec_id);
378   p_cb->p_cback = NULL;
379   return status;
380 }
381 
382 /*******************************************************************************
383  *
384  *
385  * Function    bta_jv_clear_pm_cb
386  *
387  * Description clears jv pm control block and optionally calls
388  *             bta_sys_conn_close()
389  *             In general close_conn should be set to true to remove registering
390  *             with dm pm!
391  *
392  * WARNING:    Make sure to clear pointer form port or l2c to this control block
393  *             too!
394  *
395  ******************************************************************************/
bta_jv_clear_pm_cb(tBTA_JV_PM_CB * p_pm_cb,bool close_conn)396 static void bta_jv_clear_pm_cb(tBTA_JV_PM_CB* p_pm_cb, bool close_conn) {
397   /* needs to be called if registered with bta pm, otherwise we may run out of
398    * dm pm slots! */
399   if (close_conn)
400     bta_sys_conn_close(BTA_ID_JV, p_pm_cb->app_id, p_pm_cb->peer_bd_addr);
401   p_pm_cb->state = BTA_JV_PM_FREE_ST;
402   p_pm_cb->app_id = BTA_JV_PM_ALL;
403   p_pm_cb->handle = BTA_JV_PM_HANDLE_CLEAR;
404   p_pm_cb->peer_bd_addr = RawAddress::kEmpty;
405 }
406 
407 /*******************************************************************************
408  *
409  * Function     bta_jv_free_set_pm_profile_cb
410  *
411  * Description  free pm profile control block
412  *
413  * Returns     BTA_JV_SUCCESS if cb has been freed correctly,
414  *             BTA_JV_FAILURE in case of no profile has been registered or
415  *             already freed
416  *
417  ******************************************************************************/
bta_jv_free_set_pm_profile_cb(uint32_t jv_handle)418 static tBTA_JV_STATUS bta_jv_free_set_pm_profile_cb(uint32_t jv_handle) {
419   tBTA_JV_STATUS status = BTA_JV_FAILURE;
420   tBTA_JV_PM_CB** p_cb;
421   int i, j, bd_counter = 0, appid_counter = 0;
422 
423   for (i = 0; i < BTA_JV_PM_MAX_NUM; i++) {
424     p_cb = NULL;
425     if ((bta_jv_cb.pm_cb[i].state != BTA_JV_PM_FREE_ST) &&
426         (jv_handle == bta_jv_cb.pm_cb[i].handle)) {
427       for (j = 0; j < BTA_JV_PM_MAX_NUM; j++) {
428         if (bta_jv_cb.pm_cb[j].peer_bd_addr == bta_jv_cb.pm_cb[i].peer_bd_addr)
429           bd_counter++;
430         if (bta_jv_cb.pm_cb[j].app_id == bta_jv_cb.pm_cb[i].app_id)
431           appid_counter++;
432       }
433 
434       APPL_TRACE_API(
435           "%s(jv_handle: 0x%2x), idx: %d, "
436           "app_id: 0x%x",
437           __func__, jv_handle, i, bta_jv_cb.pm_cb[i].app_id);
438       APPL_TRACE_API(
439           "%s, bd_counter = %d, "
440           "appid_counter = %d",
441           __func__, bd_counter, appid_counter);
442       if (bd_counter > 1) {
443         bta_jv_pm_conn_idle(&bta_jv_cb.pm_cb[i]);
444       }
445 
446       if (bd_counter <= 1 || (appid_counter <= 1)) {
447         bta_jv_clear_pm_cb(&bta_jv_cb.pm_cb[i], true);
448       } else {
449         bta_jv_clear_pm_cb(&bta_jv_cb.pm_cb[i], false);
450       }
451 
452       if (BTA_JV_RFCOMM_MASK & jv_handle) {
453         uint32_t hi =
454             ((jv_handle & BTA_JV_RFC_HDL_MASK) & ~BTA_JV_RFCOMM_MASK) - 1;
455         uint32_t si = BTA_JV_RFC_HDL_TO_SIDX(jv_handle);
456         if (hi < BTA_JV_MAX_RFC_CONN && bta_jv_cb.rfc_cb[hi].p_cback &&
457             si < BTA_JV_MAX_RFC_SR_SESSION &&
458             bta_jv_cb.rfc_cb[hi].rfc_hdl[si]) {
459           tBTA_JV_PCB* p_pcb =
460               bta_jv_rfc_port_to_pcb(bta_jv_cb.rfc_cb[hi].rfc_hdl[si]);
461           if (p_pcb) {
462             if (NULL == p_pcb->p_pm_cb)
463               APPL_TRACE_WARNING(
464                   "%s(jv_handle:"
465                   " 0x%x):port_handle: 0x%x, p_pm_cb: %d: no link to "
466                   "pm_cb?",
467                   __func__, jv_handle, p_pcb->port_handle, i);
468             p_cb = &p_pcb->p_pm_cb;
469           }
470         }
471       } else {
472         if (jv_handle < BTA_JV_MAX_L2C_CONN) {
473           tBTA_JV_L2C_CB* p_l2c_cb = &bta_jv_cb.l2c_cb[jv_handle];
474           if (NULL == p_l2c_cb->p_pm_cb)
475             APPL_TRACE_WARNING(
476                 "%s(jv_handle: "
477                 "0x%x): p_pm_cb: %d: no link to pm_cb?",
478                 __func__, jv_handle, i);
479           p_cb = &p_l2c_cb->p_pm_cb;
480         }
481       }
482       if (p_cb) {
483         *p_cb = NULL;
484         status = BTA_JV_SUCCESS;
485       }
486     }
487   }
488   return status;
489 }
490 
491 /*******************************************************************************
492  *
493  * Function    bta_jv_alloc_set_pm_profile_cb
494  *
495  * Description set PM profile control block
496  *
497  * Returns     pointer to allocated cb or NULL in case of failure
498  *
499  ******************************************************************************/
bta_jv_alloc_set_pm_profile_cb(uint32_t jv_handle,tBTA_JV_PM_ID app_id)500 static tBTA_JV_PM_CB* bta_jv_alloc_set_pm_profile_cb(uint32_t jv_handle,
501                                                      tBTA_JV_PM_ID app_id) {
502   bool bRfcHandle = (jv_handle & BTA_JV_RFCOMM_MASK) != 0;
503   RawAddress peer_bd_addr;
504   int i, j;
505   tBTA_JV_PM_CB** pp_cb;
506 
507   for (i = 0; i < BTA_JV_PM_MAX_NUM; i++) {
508     pp_cb = NULL;
509     if (bta_jv_cb.pm_cb[i].state == BTA_JV_PM_FREE_ST) {
510       /* rfc handle bd addr retrieval requires core stack handle */
511       if (bRfcHandle) {
512         for (j = 0; j < BTA_JV_MAX_RFC_CONN; j++) {
513           if (jv_handle == bta_jv_cb.port_cb[j].handle) {
514             pp_cb = &bta_jv_cb.port_cb[j].p_pm_cb;
515             if (PORT_SUCCESS !=
516                 PORT_CheckConnection(bta_jv_cb.port_cb[j].port_handle,
517                                      peer_bd_addr, NULL))
518               i = BTA_JV_PM_MAX_NUM;
519             break;
520           }
521         }
522       } else {
523         /* use jv handle for l2cap bd address retrieval */
524         for (j = 0; j < BTA_JV_MAX_L2C_CONN; j++) {
525           if (jv_handle == bta_jv_cb.l2c_cb[j].handle) {
526             pp_cb = &bta_jv_cb.l2c_cb[j].p_pm_cb;
527             const RawAddress* p_bd_addr =
528                 GAP_ConnGetRemoteAddr((uint16_t)jv_handle);
529             if (p_bd_addr)
530               peer_bd_addr = *p_bd_addr;
531             else
532               i = BTA_JV_PM_MAX_NUM;
533             break;
534           }
535         }
536       }
537       APPL_TRACE_API(
538           "bta_jv_alloc_set_pm_profile_cb(handle 0x%2x, app_id %d): "
539           "idx: %d, (BTA_JV_PM_MAX_NUM: %d), pp_cb: 0x%x",
540           jv_handle, app_id, i, BTA_JV_PM_MAX_NUM, pp_cb);
541       break;
542     }
543   }
544 
545   if ((i != BTA_JV_PM_MAX_NUM) && (NULL != pp_cb)) {
546     *pp_cb = &bta_jv_cb.pm_cb[i];
547     bta_jv_cb.pm_cb[i].handle = jv_handle;
548     bta_jv_cb.pm_cb[i].app_id = app_id;
549     bta_jv_cb.pm_cb[i].peer_bd_addr = peer_bd_addr;
550     bta_jv_cb.pm_cb[i].state = BTA_JV_PM_IDLE_ST;
551     return &bta_jv_cb.pm_cb[i];
552   }
553   APPL_TRACE_WARNING(
554       "bta_jv_alloc_set_pm_profile_cb(jv_handle: 0x%x, app_id: %d) "
555       "return NULL",
556       jv_handle, app_id);
557   return (tBTA_JV_PM_CB*)NULL;
558 }
559 
560 /*******************************************************************************
561  *
562  * Function     bta_jv_check_psm
563  *
564  * Description  for now use only the legal PSM per JSR82 spec
565  *
566  * Returns      true, if allowed
567  *
568  ******************************************************************************/
bta_jv_check_psm(uint16_t psm)569 bool bta_jv_check_psm(uint16_t psm) {
570   bool ret = false;
571 
572   if (L2C_IS_VALID_PSM(psm)) {
573     if (psm < 0x1001) {
574       /* see if this is defined by spec */
575       switch (psm) {
576         case SDP_PSM:       /* 1 */
577         case BT_PSM_RFCOMM: /* 3 */
578           /* do not allow java app to use these 2 PSMs */
579           break;
580 
581         case TCS_PSM_INTERCOM: /* 5 */
582         case TCS_PSM_CORDLESS: /* 7 */
583           if (false == bta_sys_is_register(BTA_ID_CT) &&
584               false == bta_sys_is_register(BTA_ID_CG))
585             ret = true;
586           break;
587 
588         case BT_PSM_BNEP: /* F */
589           if (false == bta_sys_is_register(BTA_ID_PAN)) ret = true;
590           break;
591 
592         case HID_PSM_CONTROL:   /* 0x11 */
593         case HID_PSM_INTERRUPT: /* 0x13 */
594           // FIX: allow HID Device and HID Host to coexist
595           if (false == bta_sys_is_register(BTA_ID_HD) ||
596               false == bta_sys_is_register(BTA_ID_HH))
597             ret = true;
598           break;
599 
600         case AVCT_PSM: /* 0x17 */
601         case AVDT_PSM: /* 0x19 */
602           if ((false == bta_sys_is_register(BTA_ID_AV)) &&
603               (false == bta_sys_is_register(BTA_ID_AVK)))
604             ret = true;
605           break;
606 
607         default:
608           ret = true;
609           break;
610       }
611     } else {
612       ret = true;
613     }
614   }
615   return ret;
616 }
617 
618 /*******************************************************************************
619  *
620  * Function     bta_jv_enable
621  *
622  * Description  Initialises the JAVA I/F
623  *
624  * Returns      void
625  *
626  ******************************************************************************/
bta_jv_enable(tBTA_JV_MSG * p_data)627 void bta_jv_enable(tBTA_JV_MSG* p_data) {
628   tBTA_JV_STATUS status = BTA_JV_SUCCESS;
629   bta_jv_cb.p_dm_cback = p_data->enable.p_cback;
630   tBTA_JV bta_jv;
631   bta_jv.status = status;
632   bta_jv_cb.p_dm_cback(BTA_JV_ENABLE_EVT, &bta_jv, 0);
633   memset(bta_jv_cb.free_psm_list, 0, sizeof(bta_jv_cb.free_psm_list));
634 }
635 
636 /*******************************************************************************
637  *
638  * Function     bta_jv_disable
639  *
640  * Description  Disables the BT device manager
641  *              free the resources used by java
642  *
643  * Returns      void
644  *
645  ******************************************************************************/
bta_jv_disable(UNUSED_ATTR tBTA_JV_MSG * p_data)646 void bta_jv_disable(UNUSED_ATTR tBTA_JV_MSG* p_data) {
647   APPL_TRACE_ERROR("%s", __func__);
648 }
649 
650 /**
651  * We keep a list of PSM's that have been freed from JAVA, for reuse.
652  * This function will return a free PSM, and delete it from the free
653  * list.
654  * If no free PSMs exist, 0 will be returned.
655  */
bta_jv_get_free_psm()656 static uint16_t bta_jv_get_free_psm() {
657   const int cnt =
658       sizeof(bta_jv_cb.free_psm_list) / sizeof(bta_jv_cb.free_psm_list[0]);
659   for (int i = 0; i < cnt; i++) {
660     uint16_t psm = bta_jv_cb.free_psm_list[i];
661     if (psm != 0) {
662       APPL_TRACE_DEBUG("%s(): Reusing PSM: 0x%04d", __func__, psm)
663       bta_jv_cb.free_psm_list[i] = 0;
664       return psm;
665     }
666   }
667   return 0;
668 }
669 
bta_jv_set_free_psm(uint16_t psm)670 static void bta_jv_set_free_psm(uint16_t psm) {
671   int free_index = -1;
672   const int cnt =
673       sizeof(bta_jv_cb.free_psm_list) / sizeof(bta_jv_cb.free_psm_list[0]);
674   for (int i = 0; i < cnt; i++) {
675     if (bta_jv_cb.free_psm_list[i] == 0) {
676       free_index = i;
677     } else if (psm == bta_jv_cb.free_psm_list[i]) {
678       return;  // PSM already freed?
679     }
680   }
681   if (free_index != -1) {
682     bta_jv_cb.free_psm_list[free_index] = psm;
683     APPL_TRACE_DEBUG("%s(): Recycling PSM: 0x%04d", __func__, psm)
684   } else {
685     APPL_TRACE_ERROR("%s unable to free psm 0x%x no more free slots", __func__,
686                      psm);
687   }
688 }
689 
690 /*******************************************************************************
691  *
692  * Function     bta_jv_get_channel_id
693  *
694  * Description  Obtain a free SCN (Server Channel Number)
695  *              (RFCOMM channel or L2CAP PSM)
696  *
697  * Returns      void
698  *
699  ******************************************************************************/
bta_jv_get_channel_id(tBTA_JV_MSG * p_data)700 void bta_jv_get_channel_id(tBTA_JV_MSG* p_data) {
701   uint16_t psm = 0;
702 
703   switch (p_data->alloc_channel.type) {
704     case BTA_JV_CONN_TYPE_RFCOMM: {
705       int32_t channel = p_data->alloc_channel.channel;
706       uint8_t scn = 0;
707       if (channel > 0) {
708         if (BTM_TryAllocateSCN(channel) == false) {
709           APPL_TRACE_ERROR("rfc channel:%d already in use or invalid", channel);
710           channel = 0;
711         }
712       } else {
713         channel = BTM_AllocateSCN();
714         if (channel == 0) {
715           APPL_TRACE_ERROR("run out of rfc channels");
716           channel = 0;
717         }
718       }
719       if (channel != 0) {
720         bta_jv_cb.scn[channel - 1] = true;
721         scn = (uint8_t)channel;
722       }
723       if (bta_jv_cb.p_dm_cback) {
724         tBTA_JV bta_jv;
725         bta_jv.scn = scn;
726         bta_jv_cb.p_dm_cback(BTA_JV_GET_SCN_EVT, &bta_jv,
727                              p_data->alloc_channel.rfcomm_slot_id);
728       }
729       return;
730     }
731     case BTA_JV_CONN_TYPE_L2CAP:
732       psm = bta_jv_get_free_psm();
733       if (psm == 0) {
734         psm = L2CA_AllocatePSM();
735         APPL_TRACE_DEBUG("%s() returned PSM: 0x%04x", __func__, psm);
736       }
737       break;
738     case BTA_JV_CONN_TYPE_L2CAP_LE:
739       break;
740     default:
741       break;
742   }
743 
744   if (bta_jv_cb.p_dm_cback) {
745     tBTA_JV bta_jv;
746     bta_jv.psm = psm;
747     bta_jv_cb.p_dm_cback(BTA_JV_GET_PSM_EVT, &bta_jv,
748                          p_data->alloc_channel.l2cap_socket_id);
749   }
750 }
751 
752 /*******************************************************************************
753  *
754  * Function     bta_jv_free_scn
755  *
756  * Description  free a SCN
757  *
758  * Returns      void
759  *
760  ******************************************************************************/
bta_jv_free_scn(tBTA_JV_MSG * p_data)761 void bta_jv_free_scn(tBTA_JV_MSG* p_data) {
762   uint16_t scn = p_data->free_channel.scn;
763 
764   switch (p_data->free_channel.type) {
765     case BTA_JV_CONN_TYPE_RFCOMM: {
766       if (scn > 0 && scn <= BTA_JV_MAX_SCN && bta_jv_cb.scn[scn - 1]) {
767         /* this scn is used by JV */
768         bta_jv_cb.scn[scn - 1] = false;
769         BTM_FreeSCN(scn);
770       }
771       break;
772     }
773     case BTA_JV_CONN_TYPE_L2CAP:
774       bta_jv_set_free_psm(scn);
775       break;
776     case BTA_JV_CONN_TYPE_L2CAP_LE:
777       // TODO: Not yet implemented...
778       break;
779     default:
780       break;
781   }
782 }
shorten_sdp_uuid(const tBT_UUID * u)783 static inline tBT_UUID shorten_sdp_uuid(const tBT_UUID* u) {
784   static uint8_t bt_base_uuid[] = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
785                                    0x10, 0x00, 0x80, 0x00, 0x00, 0x80,
786                                    0x5F, 0x9B, 0x34, 0xFB};
787 
788   logu("in, uuid:", u->uu.uuid128);
789   APPL_TRACE_DEBUG("uuid len:%d", u->len);
790   if (u->len == 16) {
791     if (memcmp(&u->uu.uuid128[4], &bt_base_uuid[4], 12) == 0) {
792       tBT_UUID su;
793       memset(&su, 0, sizeof(su));
794       if (u->uu.uuid128[0] == 0 && u->uu.uuid128[1] == 0) {
795         su.len = 2;
796         uint16_t u16;
797         memcpy(&u16, &u->uu.uuid128[2], sizeof(u16));
798         su.uu.uuid16 = ntohs(u16);
799         APPL_TRACE_DEBUG("shorten to 16 bits uuid: %x", su.uu.uuid16);
800       } else {
801         su.len = 4;
802         uint32_t u32;
803         memcpy(&u32, &u->uu.uuid128[0], sizeof(u32));
804         su.uu.uuid32 = ntohl(u32);
805         APPL_TRACE_DEBUG("shorten to 32 bits uuid: %x", su.uu.uuid32);
806       }
807       return su;
808     }
809   }
810   APPL_TRACE_DEBUG("cannot shorten none-reserved 128 bits uuid");
811   return *u;
812 }
813 
814 /*******************************************************************************
815  *
816  * Function     bta_jv_start_discovery_cback
817  *
818  * Description  Callback for Start Discovery
819  *
820  * Returns      void
821  *
822  ******************************************************************************/
bta_jv_start_discovery_cback(uint16_t result,void * user_data)823 static void bta_jv_start_discovery_cback(uint16_t result, void* user_data) {
824   tBTA_JV_STATUS status;
825   uint32_t* p_rfcomm_slot_id = static_cast<uint32_t*>(user_data);
826 
827   APPL_TRACE_DEBUG("bta_jv_start_discovery_cback res: 0x%x", result);
828 
829   bta_jv_cb.sdp_active = BTA_JV_SDP_ACT_NONE;
830   if (bta_jv_cb.p_dm_cback) {
831     tBTA_JV_DISCOVERY_COMP dcomp;
832     dcomp.scn = 0;
833     status = BTA_JV_FAILURE;
834     if (result == SDP_SUCCESS || result == SDP_DB_FULL) {
835       tSDP_DISC_REC* p_sdp_rec = NULL;
836       tSDP_PROTOCOL_ELEM pe;
837       logu("bta_jv_cb.uuid", bta_jv_cb.uuid.uu.uuid128);
838       tBT_UUID su = shorten_sdp_uuid(&bta_jv_cb.uuid);
839       logu("shorten uuid:", su.uu.uuid128);
840       p_sdp_rec =
841           SDP_FindServiceUUIDInDb(p_bta_jv_cfg->p_sdp_db, &su, p_sdp_rec);
842       APPL_TRACE_DEBUG("p_sdp_rec:%p", p_sdp_rec);
843       if (p_sdp_rec &&
844           SDP_FindProtocolListElemInRec(p_sdp_rec, UUID_PROTOCOL_RFCOMM, &pe)) {
845         dcomp.scn = (uint8_t)pe.params[0];
846         status = BTA_JV_SUCCESS;
847       }
848     }
849 
850     dcomp.status = status;
851     tBTA_JV bta_jv;
852     bta_jv.disc_comp = dcomp;
853     bta_jv_cb.p_dm_cback(BTA_JV_DISCOVERY_COMP_EVT, &bta_jv, *p_rfcomm_slot_id);
854     osi_free(p_rfcomm_slot_id);
855   }
856 }
857 
858 /*******************************************************************************
859  *
860  * Function     bta_jv_start_discovery
861  *
862  * Description  Discovers services on a remote device
863  *
864  * Returns      void
865  *
866  ******************************************************************************/
bta_jv_start_discovery(tBTA_JV_MSG * p_data)867 void bta_jv_start_discovery(tBTA_JV_MSG* p_data) {
868   tBTA_JV_STATUS status = BTA_JV_FAILURE;
869   APPL_TRACE_DEBUG("bta_jv_start_discovery in, sdp_active:%d",
870                    bta_jv_cb.sdp_active);
871   if (bta_jv_cb.sdp_active != BTA_JV_SDP_ACT_NONE) {
872     /* SDP is still in progress */
873     status = BTA_JV_BUSY;
874     if (bta_jv_cb.p_dm_cback) {
875       tBTA_JV bta_jv;
876       bta_jv.status = status;
877       bta_jv_cb.p_dm_cback(BTA_JV_DISCOVERY_COMP_EVT, &bta_jv,
878                            p_data->start_discovery.rfcomm_slot_id);
879     }
880     return;
881   }
882 
883   /* init the database/set up the filter */
884   APPL_TRACE_DEBUG(
885       "call SDP_InitDiscoveryDb, p_data->start_discovery.num_uuid:%d",
886       p_data->start_discovery.num_uuid);
887   SDP_InitDiscoveryDb(p_bta_jv_cfg->p_sdp_db, p_bta_jv_cfg->sdp_db_size,
888                       p_data->start_discovery.num_uuid,
889                       p_data->start_discovery.uuid_list, 0, NULL);
890 
891   /* tell SDP to keep the raw data */
892   p_bta_jv_cfg->p_sdp_db->raw_data = p_bta_jv_cfg->p_sdp_raw_data;
893   p_bta_jv_cfg->p_sdp_db->raw_size = p_bta_jv_cfg->sdp_raw_size;
894 
895   bta_jv_cb.p_sel_raw_data = 0;
896   bta_jv_cb.uuid = p_data->start_discovery.uuid_list[0];
897 
898   bta_jv_cb.sdp_active = BTA_JV_SDP_ACT_YES;
899 
900   uint32_t* rfcomm_slot_id = (uint32_t*)osi_malloc(sizeof(uint32_t));
901   *rfcomm_slot_id = p_data->start_discovery.rfcomm_slot_id;
902 
903   if (!SDP_ServiceSearchAttributeRequest2(
904           p_data->start_discovery.bd_addr, p_bta_jv_cfg->p_sdp_db,
905           bta_jv_start_discovery_cback, (void*)rfcomm_slot_id)) {
906     bta_jv_cb.sdp_active = BTA_JV_SDP_ACT_NONE;
907     /* failed to start SDP. report the failure right away */
908     if (bta_jv_cb.p_dm_cback) {
909       tBTA_JV bta_jv;
910       bta_jv.status = status;
911       bta_jv_cb.p_dm_cback(BTA_JV_DISCOVERY_COMP_EVT, &bta_jv,
912                            p_data->start_discovery.rfcomm_slot_id);
913     }
914   }
915   /*
916   else report the result when the cback is called
917   */
918 }
919 
920 /*******************************************************************************
921  *
922  * Function     bta_jv_create_record
923  *
924  * Description  Create an SDP record with the given attributes
925  *
926  * Returns      void
927  *
928  ******************************************************************************/
bta_jv_create_record(tBTA_JV_MSG * p_data)929 void bta_jv_create_record(tBTA_JV_MSG* p_data) {
930   tBTA_JV_API_CREATE_RECORD* cr = &(p_data->create_record);
931   tBTA_JV_CREATE_RECORD evt_data;
932   evt_data.status = BTA_JV_SUCCESS;
933   if (bta_jv_cb.p_dm_cback) {
934     // callback immediately to create the sdp record in stack thread context
935     tBTA_JV bta_jv;
936     bta_jv.create_rec = evt_data;
937     bta_jv_cb.p_dm_cback(BTA_JV_CREATE_RECORD_EVT, &bta_jv, cr->rfcomm_slot_id);
938   }
939 }
940 
941 /*******************************************************************************
942  *
943  * Function     bta_jv_delete_record
944  *
945  * Description  Delete an SDP record
946  *
947  *
948  * Returns      void
949  *
950  ******************************************************************************/
bta_jv_delete_record(tBTA_JV_MSG * p_data)951 void bta_jv_delete_record(tBTA_JV_MSG* p_data) {
952   tBTA_JV_API_ADD_ATTRIBUTE* dr = &(p_data->add_attr);
953   if (dr->handle) {
954     /* this is a record created by btif layer*/
955     SDP_DeleteRecord(dr->handle);
956   }
957 }
958 
959 /*******************************************************************************
960  *
961  * Function     bta_jv_l2cap_client_cback
962  *
963  * Description  handles the l2cap client events
964  *
965  * Returns      void
966  *
967  ******************************************************************************/
bta_jv_l2cap_client_cback(uint16_t gap_handle,uint16_t event)968 static void bta_jv_l2cap_client_cback(uint16_t gap_handle, uint16_t event) {
969   tBTA_JV_L2C_CB* p_cb = &bta_jv_cb.l2c_cb[gap_handle];
970   tBTA_JV evt_data;
971 
972   if (gap_handle >= BTA_JV_MAX_L2C_CONN && !p_cb->p_cback) return;
973 
974   APPL_TRACE_DEBUG("%s: %d evt:x%x", __func__, gap_handle, event);
975   evt_data.l2c_open.status = BTA_JV_SUCCESS;
976   evt_data.l2c_open.handle = gap_handle;
977 
978   switch (event) {
979     case GAP_EVT_CONN_OPENED:
980       evt_data.l2c_open.rem_bda = *GAP_ConnGetRemoteAddr(gap_handle);
981       evt_data.l2c_open.tx_mtu = GAP_ConnGetRemMtuSize(gap_handle);
982       p_cb->state = BTA_JV_ST_CL_OPEN;
983       p_cb->p_cback(BTA_JV_L2CAP_OPEN_EVT, &evt_data, p_cb->l2cap_socket_id);
984       break;
985 
986     case GAP_EVT_CONN_CLOSED:
987       p_cb->state = BTA_JV_ST_NONE;
988       bta_jv_free_sec_id(&p_cb->sec_id);
989       evt_data.l2c_close.async = true;
990       p_cb->p_cback(BTA_JV_L2CAP_CLOSE_EVT, &evt_data, p_cb->l2cap_socket_id);
991       p_cb->p_cback = NULL;
992       break;
993 
994     case GAP_EVT_CONN_DATA_AVAIL:
995       evt_data.data_ind.handle = gap_handle;
996       /* Reset idle timer to avoid requesting sniff mode while receiving data */
997       bta_jv_pm_conn_busy(p_cb->p_pm_cb);
998       p_cb->p_cback(BTA_JV_L2CAP_DATA_IND_EVT, &evt_data,
999                     p_cb->l2cap_socket_id);
1000       bta_jv_pm_conn_idle(p_cb->p_pm_cb);
1001       break;
1002 
1003     case GAP_EVT_TX_EMPTY:
1004       bta_jv_pm_conn_idle(p_cb->p_pm_cb);
1005       break;
1006 
1007     case GAP_EVT_CONN_CONGESTED:
1008     case GAP_EVT_CONN_UNCONGESTED:
1009       p_cb->cong = (event == GAP_EVT_CONN_CONGESTED) ? true : false;
1010       evt_data.l2c_cong.cong = p_cb->cong;
1011       p_cb->p_cback(BTA_JV_L2CAP_CONG_EVT, &evt_data, p_cb->l2cap_socket_id);
1012       break;
1013 
1014     default:
1015       break;
1016   }
1017 }
1018 
1019 /*******************************************************************************
1020  *
1021  * Function     bta_jv_l2cap_connect
1022  *
1023  * Description  makes an l2cap client connection
1024  *
1025  * Returns      void
1026  *
1027  ******************************************************************************/
bta_jv_l2cap_connect(tBTA_JV_MSG * p_data)1028 void bta_jv_l2cap_connect(tBTA_JV_MSG* p_data) {
1029   tBTA_JV_L2C_CB* p_cb;
1030   tBTA_JV_L2CAP_CL_INIT evt_data;
1031   uint16_t handle = GAP_INVALID_HANDLE;
1032   uint8_t sec_id;
1033   tL2CAP_CFG_INFO cfg;
1034   tBTA_JV_API_L2CAP_CONNECT* cc = &(p_data->l2cap_connect);
1035   uint8_t chan_mode_mask = GAP_FCR_CHAN_OPT_BASIC;
1036   tL2CAP_ERTM_INFO* ertm_info = NULL;
1037 
1038   memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
1039 
1040   if (cc->has_cfg == true) {
1041     cfg = cc->cfg;
1042     if (cfg.fcr_present && cfg.fcr.mode == L2CAP_FCR_ERTM_MODE) {
1043       chan_mode_mask = GAP_FCR_CHAN_OPT_ERTM;
1044     }
1045   }
1046 
1047   if (cc->has_ertm_info == true) {
1048     ertm_info = &(cc->ertm_info);
1049   }
1050 
1051   /* We need to use this value for MTU to be able to handle cases where cfg is
1052    * not set in req. */
1053   cfg.mtu_present = true;
1054   cfg.mtu = cc->rx_mtu;
1055 
1056   /* TODO: DM role manager
1057   L2CA_SetDesireRole(cc->role);
1058   */
1059 
1060   sec_id = bta_jv_alloc_sec_id();
1061   evt_data.sec_id = sec_id;
1062   evt_data.status = BTA_JV_FAILURE;
1063 
1064   if (sec_id) {
1065     /* PSM checking is not required for LE COC */
1066     if ((cc->type != BTA_JV_CONN_TYPE_L2CAP) ||
1067         (bta_jv_check_psm(cc->remote_psm))) /* allowed */
1068     {
1069       handle = GAP_ConnOpen("", sec_id, 0, &cc->peer_bd_addr, cc->remote_psm,
1070                             &cfg, ertm_info, cc->sec_mask, chan_mode_mask,
1071                             bta_jv_l2cap_client_cback, cc->type);
1072       if (handle != GAP_INVALID_HANDLE) {
1073         evt_data.status = BTA_JV_SUCCESS;
1074       }
1075     }
1076   }
1077 
1078   if (evt_data.status == BTA_JV_SUCCESS) {
1079     p_cb = &bta_jv_cb.l2c_cb[handle];
1080     p_cb->handle = handle;
1081     p_cb->p_cback = cc->p_cback;
1082     p_cb->l2cap_socket_id = cc->l2cap_socket_id;
1083     p_cb->psm = 0; /* not a server */
1084     p_cb->sec_id = sec_id;
1085     p_cb->state = BTA_JV_ST_CL_OPENING;
1086   } else {
1087     bta_jv_free_sec_id(&sec_id);
1088   }
1089 
1090   evt_data.handle = handle;
1091   if (cc->p_cback) {
1092     tBTA_JV bta_jv;
1093     bta_jv.l2c_cl_init = evt_data;
1094     cc->p_cback(BTA_JV_L2CAP_CL_INIT_EVT, &bta_jv, cc->l2cap_socket_id);
1095   }
1096 }
1097 
1098 /*******************************************************************************
1099  *
1100  * Function     bta_jv_l2cap_close
1101  *
1102  * Description  Close an L2CAP client connection
1103  *
1104  * Returns      void
1105  *
1106  ******************************************************************************/
bta_jv_l2cap_close(tBTA_JV_MSG * p_data)1107 void bta_jv_l2cap_close(tBTA_JV_MSG* p_data) {
1108   tBTA_JV_L2CAP_CLOSE evt_data;
1109   tBTA_JV_API_L2CAP_CLOSE* cc = &(p_data->l2cap_close);
1110   tBTA_JV_L2CAP_CBACK* p_cback = cc->p_cb->p_cback;
1111   uint32_t l2cap_socket_id = cc->p_cb->l2cap_socket_id;
1112 
1113   evt_data.handle = cc->handle;
1114   evt_data.status = bta_jv_free_l2c_cb(cc->p_cb);
1115   evt_data.async = false;
1116 
1117   if (p_cback) {
1118     tBTA_JV bta_jv;
1119     bta_jv.l2c_close = evt_data;
1120     p_cback(BTA_JV_L2CAP_CLOSE_EVT, &bta_jv, l2cap_socket_id);
1121   }
1122 }
1123 
1124 /*******************************************************************************
1125  *
1126  * Function         bta_jv_l2cap_server_cback
1127  *
1128  * Description      handles the l2cap server callback
1129  *
1130  * Returns          void
1131  *
1132  ******************************************************************************/
bta_jv_l2cap_server_cback(uint16_t gap_handle,uint16_t event)1133 static void bta_jv_l2cap_server_cback(uint16_t gap_handle, uint16_t event) {
1134   tBTA_JV_L2C_CB* p_cb = &bta_jv_cb.l2c_cb[gap_handle];
1135   tBTA_JV evt_data;
1136   tBTA_JV_L2CAP_CBACK* p_cback;
1137   uint32_t socket_id;
1138 
1139   if (gap_handle >= BTA_JV_MAX_L2C_CONN && !p_cb->p_cback) return;
1140 
1141   APPL_TRACE_DEBUG("%s: %d evt:x%x", __func__, gap_handle, event);
1142   evt_data.l2c_open.status = BTA_JV_SUCCESS;
1143   evt_data.l2c_open.handle = gap_handle;
1144 
1145   switch (event) {
1146     case GAP_EVT_CONN_OPENED:
1147       evt_data.l2c_open.rem_bda = *GAP_ConnGetRemoteAddr(gap_handle);
1148       evt_data.l2c_open.tx_mtu = GAP_ConnGetRemMtuSize(gap_handle);
1149       p_cb->state = BTA_JV_ST_SR_OPEN;
1150       p_cb->p_cback(BTA_JV_L2CAP_OPEN_EVT, &evt_data, p_cb->l2cap_socket_id);
1151       break;
1152 
1153     case GAP_EVT_CONN_CLOSED:
1154       evt_data.l2c_close.async = true;
1155       evt_data.l2c_close.handle = p_cb->handle;
1156       p_cback = p_cb->p_cback;
1157       socket_id = p_cb->l2cap_socket_id;
1158       evt_data.l2c_close.status = bta_jv_free_l2c_cb(p_cb);
1159       p_cback(BTA_JV_L2CAP_CLOSE_EVT, &evt_data, socket_id);
1160       break;
1161 
1162     case GAP_EVT_CONN_DATA_AVAIL:
1163       evt_data.data_ind.handle = gap_handle;
1164       /* Reset idle timer to avoid requesting sniff mode while receiving data */
1165       bta_jv_pm_conn_busy(p_cb->p_pm_cb);
1166       p_cb->p_cback(BTA_JV_L2CAP_DATA_IND_EVT, &evt_data,
1167                     p_cb->l2cap_socket_id);
1168       bta_jv_pm_conn_idle(p_cb->p_pm_cb);
1169       break;
1170 
1171     case GAP_EVT_TX_EMPTY:
1172       bta_jv_pm_conn_idle(p_cb->p_pm_cb);
1173       break;
1174 
1175     case GAP_EVT_CONN_CONGESTED:
1176     case GAP_EVT_CONN_UNCONGESTED:
1177       p_cb->cong = (event == GAP_EVT_CONN_CONGESTED) ? true : false;
1178       evt_data.l2c_cong.cong = p_cb->cong;
1179       p_cb->p_cback(BTA_JV_L2CAP_CONG_EVT, &evt_data, p_cb->l2cap_socket_id);
1180       break;
1181 
1182     default:
1183       break;
1184   }
1185 }
1186 
1187 /*******************************************************************************
1188  *
1189  * Function     bta_jv_l2cap_start_server
1190  *
1191  * Description  starts an L2CAP server
1192  *
1193  * Returns      void
1194  *
1195  ******************************************************************************/
bta_jv_l2cap_start_server(tBTA_JV_MSG * p_data)1196 void bta_jv_l2cap_start_server(tBTA_JV_MSG* p_data) {
1197   tBTA_JV_L2C_CB* p_cb;
1198   uint8_t sec_id;
1199   uint16_t handle;
1200   tL2CAP_CFG_INFO cfg;
1201   tBTA_JV_L2CAP_START evt_data;
1202   tBTA_JV_API_L2CAP_SERVER* ls = &(p_data->l2cap_server);
1203   uint8_t chan_mode_mask = GAP_FCR_CHAN_OPT_BASIC;
1204   tL2CAP_ERTM_INFO* ertm_info = NULL;
1205 
1206   memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
1207 
1208   if (ls->has_cfg == true) {
1209     cfg = ls->cfg;
1210     if (cfg.fcr_present && cfg.fcr.mode == L2CAP_FCR_ERTM_MODE) {
1211       chan_mode_mask = GAP_FCR_CHAN_OPT_ERTM;
1212     }
1213   }
1214 
1215   if (ls->has_ertm_info == true) {
1216     ertm_info = &(ls->ertm_info);
1217   }
1218 
1219   // FIX: MTU=0 means not present
1220   if (ls->rx_mtu > 0) {
1221     cfg.mtu_present = true;
1222     cfg.mtu = ls->rx_mtu;
1223   } else {
1224     cfg.mtu_present = false;
1225     cfg.mtu = 0;
1226   }
1227 
1228   /* TODO DM role manager
1229   L2CA_SetDesireRole(ls->role);
1230   */
1231 
1232   sec_id = bta_jv_alloc_sec_id();
1233   /* PSM checking is not required for LE COC */
1234   if (0 == sec_id || ((ls->type == BTA_JV_CONN_TYPE_L2CAP) &&
1235                       (false == bta_jv_check_psm(ls->local_psm))) ||
1236       (handle = GAP_ConnOpen("JV L2CAP", sec_id, 1, nullptr, ls->local_psm,
1237                              &cfg, ertm_info, ls->sec_mask, chan_mode_mask,
1238                              bta_jv_l2cap_server_cback, ls->type)) ==
1239           GAP_INVALID_HANDLE) {
1240     bta_jv_free_sec_id(&sec_id);
1241     evt_data.status = BTA_JV_FAILURE;
1242   } else {
1243     p_cb = &bta_jv_cb.l2c_cb[handle];
1244     evt_data.status = BTA_JV_SUCCESS;
1245     evt_data.handle = handle;
1246     evt_data.sec_id = sec_id;
1247     p_cb->p_cback = ls->p_cback;
1248     p_cb->l2cap_socket_id = ls->l2cap_socket_id;
1249     p_cb->handle = handle;
1250     p_cb->sec_id = sec_id;
1251     p_cb->state = BTA_JV_ST_SR_LISTEN;
1252     p_cb->psm = ls->local_psm;
1253   }
1254 
1255   if (ls->p_cback) {
1256     tBTA_JV bta_jv;
1257     bta_jv.l2c_start = evt_data;
1258     ls->p_cback(BTA_JV_L2CAP_START_EVT, &bta_jv, ls->l2cap_socket_id);
1259   }
1260 }
1261 
1262 /*******************************************************************************
1263  *
1264  * Function     bta_jv_l2cap_stop_server
1265  *
1266  * Description  stops an L2CAP server
1267  *
1268  * Returns      void
1269  *
1270  ******************************************************************************/
bta_jv_l2cap_stop_server(tBTA_JV_MSG * p_data)1271 void bta_jv_l2cap_stop_server(tBTA_JV_MSG* p_data) {
1272   tBTA_JV_L2C_CB* p_cb;
1273   tBTA_JV_L2CAP_CLOSE evt_data;
1274   tBTA_JV_API_L2CAP_SERVER* ls = &(p_data->l2cap_server);
1275   tBTA_JV_L2CAP_CBACK* p_cback;
1276   for (int i = 0; i < BTA_JV_MAX_L2C_CONN; i++) {
1277     if (bta_jv_cb.l2c_cb[i].psm == ls->local_psm) {
1278       p_cb = &bta_jv_cb.l2c_cb[i];
1279       p_cback = p_cb->p_cback;
1280       uint32_t l2cap_socket_id = p_cb->l2cap_socket_id;
1281       evt_data.handle = p_cb->handle;
1282       evt_data.status = bta_jv_free_l2c_cb(p_cb);
1283       evt_data.async = false;
1284       if (p_cback) {
1285         tBTA_JV bta_jv;
1286         bta_jv.l2c_close = evt_data;
1287         p_cback(BTA_JV_L2CAP_CLOSE_EVT, &bta_jv, l2cap_socket_id);
1288       }
1289       break;
1290     }
1291   }
1292 }
1293 
1294 /*******************************************************************************
1295  *
1296  * Function     bta_jv_l2cap_read
1297  *
1298  * Description  Read data from an L2CAP connection
1299  *
1300  * Returns      void
1301  *
1302  ******************************************************************************/
bta_jv_l2cap_read(tBTA_JV_MSG * p_data)1303 void bta_jv_l2cap_read(tBTA_JV_MSG* p_data) {
1304   tBTA_JV_L2CAP_READ evt_data;
1305   tBTA_JV_API_L2CAP_READ* rc = &(p_data->l2cap_read);
1306 
1307   evt_data.status = BTA_JV_FAILURE;
1308   evt_data.handle = rc->handle;
1309   evt_data.req_id = rc->req_id;
1310   evt_data.p_data = rc->p_data;
1311   evt_data.len = 0;
1312 
1313   if (BT_PASS ==
1314       GAP_ConnReadData(rc->handle, rc->p_data, rc->len, &evt_data.len)) {
1315     evt_data.status = BTA_JV_SUCCESS;
1316   }
1317 
1318   tBTA_JV bta_jv;
1319   bta_jv.l2c_read = evt_data;
1320   rc->p_cback(BTA_JV_L2CAP_READ_EVT, &bta_jv, rc->l2cap_socket_id);
1321 }
1322 
1323 /*******************************************************************************
1324  *
1325  * Function     bta_jv_l2cap_write
1326  *
1327  * Description  Write data to an L2CAP connection
1328  *
1329  * Returns      void
1330  *
1331  ******************************************************************************/
bta_jv_l2cap_write(tBTA_JV_MSG * p_data)1332 void bta_jv_l2cap_write(tBTA_JV_MSG* p_data) {
1333   tBTA_JV_L2CAP_WRITE evt_data;
1334   tBTA_JV_API_L2CAP_WRITE* ls = &(p_data->l2cap_write);
1335 
1336   /* As we check this callback exists before the tBTA_JV_API_L2CAP_WRITE can be
1337    * send through the
1338    * API this check should not be needed.
1339    * But the API is not designed to be used (safely at least) in a
1340    * multi-threaded scheduler, hence
1341    * if the peer device disconnects the l2cap link after the API is called, but
1342    * before this
1343    * message is handled, the ->p_cback will be cleared at this point. At first
1344    * glanch this seems
1345    * highly unlikely, but for all obex-profiles with two channels connected -
1346    * e.g. MAP, this
1347    * happens around 1 of 4 disconnects, as a disconnect on the server channel
1348    * causes a disconnect
1349    * to be send on the client (notification) channel, but at the peer typically
1350    * disconnects both
1351    * the OBEX disconnect request crosses the incoming l2cap disconnect.
1352    * If p_cback is cleared, we simply discard the data.
1353    * RISK: The caller must handle any cleanup based on another signal than
1354    * BTA_JV_L2CAP_WRITE_EVT,
1355    *       which is typically not possible, as the pointer to the allocated
1356    * buffer is stored
1357    *       in this message, and can therefore not be freed, hence we have a
1358    * mem-leak-by-design.*/
1359   if (ls->p_cb->p_cback != NULL) {
1360     evt_data.status = BTA_JV_FAILURE;
1361     evt_data.handle = ls->handle;
1362     evt_data.req_id = ls->req_id;
1363     evt_data.p_data = ls->p_data;
1364     evt_data.cong = ls->p_cb->cong;
1365     evt_data.len = 0;
1366     bta_jv_pm_conn_busy(ls->p_cb->p_pm_cb);
1367     if (!evt_data.cong &&
1368         BT_PASS ==
1369             GAP_ConnWriteData(ls->handle, ls->p_data, ls->len, &evt_data.len)) {
1370       evt_data.status = BTA_JV_SUCCESS;
1371     }
1372     tBTA_JV bta_jv;
1373     bta_jv.l2c_write = evt_data;
1374     ls->p_cb->p_cback(BTA_JV_L2CAP_WRITE_EVT, &bta_jv, ls->user_id);
1375   } else {
1376     /* As this pointer is checked in the API function, this occurs only when the
1377      * channel is
1378      * disconnected after the API function is called, but before the message is
1379      * handled. */
1380     APPL_TRACE_ERROR("%s() ls->p_cb->p_cback == NULL", __func__);
1381   }
1382 }
1383 
1384 /*******************************************************************************
1385  *
1386  * Function     bta_jv_l2cap_write_fixed
1387  *
1388  * Description  Write data to an L2CAP connection using Fixed channels
1389  *
1390  * Returns      void
1391  *
1392  ******************************************************************************/
bta_jv_l2cap_write_fixed(tBTA_JV_MSG * p_data)1393 void bta_jv_l2cap_write_fixed(tBTA_JV_MSG* p_data) {
1394   tBTA_JV_L2CAP_WRITE_FIXED evt_data;
1395   tBTA_JV_API_L2CAP_WRITE_FIXED* ls = &(p_data->l2cap_write_fixed);
1396   BT_HDR* msg =
1397       (BT_HDR*)osi_malloc(sizeof(BT_HDR) + ls->len + L2CAP_MIN_OFFSET);
1398 
1399   evt_data.status = BTA_JV_FAILURE;
1400   evt_data.channel = ls->channel;
1401   evt_data.addr = ls->addr;
1402   evt_data.req_id = ls->req_id;
1403   evt_data.p_data = ls->p_data;
1404   evt_data.len = 0;
1405 
1406   memcpy(((uint8_t*)(msg + 1)) + L2CAP_MIN_OFFSET, ls->p_data, ls->len);
1407   msg->len = ls->len;
1408   msg->offset = L2CAP_MIN_OFFSET;
1409 
1410   L2CA_SendFixedChnlData(ls->channel, ls->addr, msg);
1411 
1412   tBTA_JV bta_jv;
1413   bta_jv.l2c_write_fixed = evt_data;
1414   ls->p_cback(BTA_JV_L2CAP_WRITE_FIXED_EVT, &bta_jv, ls->user_id);
1415 }
1416 
1417 /*******************************************************************************
1418  *
1419  * Function     bta_jv_port_data_co_cback
1420  *
1421  * Description  port data callback function of rfcomm
1422  *              connections
1423  *
1424  * Returns      void
1425  *
1426  ******************************************************************************/
bta_jv_port_data_co_cback(uint16_t port_handle,uint8_t * buf,uint16_t len,int type)1427 static int bta_jv_port_data_co_cback(uint16_t port_handle, uint8_t* buf,
1428                                      uint16_t len, int type) {
1429   tBTA_JV_RFC_CB* p_cb = bta_jv_rfc_port_to_cb(port_handle);
1430   tBTA_JV_PCB* p_pcb = bta_jv_rfc_port_to_pcb(port_handle);
1431   APPL_TRACE_DEBUG("%s, p_cb:%p, p_pcb:%p, len:%d, type:%d", __func__, p_cb,
1432                    p_pcb, len, type);
1433   if (p_pcb != NULL) {
1434     switch (type) {
1435       case DATA_CO_CALLBACK_TYPE_INCOMING:
1436         return bta_co_rfc_data_incoming(p_pcb->rfcomm_slot_id, (BT_HDR*)buf);
1437       case DATA_CO_CALLBACK_TYPE_OUTGOING_SIZE:
1438         return bta_co_rfc_data_outgoing_size(p_pcb->rfcomm_slot_id, (int*)buf);
1439       case DATA_CO_CALLBACK_TYPE_OUTGOING:
1440         return bta_co_rfc_data_outgoing(p_pcb->rfcomm_slot_id, buf, len);
1441       default:
1442         APPL_TRACE_ERROR("unknown callout type:%d", type);
1443         break;
1444     }
1445   }
1446   return 0;
1447 }
1448 
1449 /*******************************************************************************
1450  *
1451  * Function     bta_jv_port_mgmt_cl_cback
1452  *
1453  * Description  callback for port mamangement function of rfcomm
1454  *              client connections
1455  *
1456  * Returns      void
1457  *
1458  ******************************************************************************/
bta_jv_port_mgmt_cl_cback(uint32_t code,uint16_t port_handle)1459 static void bta_jv_port_mgmt_cl_cback(uint32_t code, uint16_t port_handle) {
1460   tBTA_JV_RFC_CB* p_cb = bta_jv_rfc_port_to_cb(port_handle);
1461   tBTA_JV_PCB* p_pcb = bta_jv_rfc_port_to_pcb(port_handle);
1462   tBTA_JV evt_data;
1463   RawAddress rem_bda;
1464   uint16_t lcid;
1465   tBTA_JV_RFCOMM_CBACK* p_cback; /* the callback function */
1466 
1467   APPL_TRACE_DEBUG("bta_jv_port_mgmt_cl_cback:code:%d, port_handle%d", code,
1468                    port_handle);
1469   if (NULL == p_cb || NULL == p_cb->p_cback) return;
1470 
1471   APPL_TRACE_DEBUG("bta_jv_port_mgmt_cl_cback code=%d port_handle:%d handle:%d",
1472                    code, port_handle, p_cb->handle);
1473 
1474   PORT_CheckConnection(port_handle, rem_bda, &lcid);
1475 
1476   if (code == PORT_SUCCESS) {
1477     evt_data.rfc_open.handle = p_cb->handle;
1478     evt_data.rfc_open.status = BTA_JV_SUCCESS;
1479     evt_data.rfc_open.rem_bda = rem_bda;
1480     p_pcb->state = BTA_JV_ST_CL_OPEN;
1481     p_cb->p_cback(BTA_JV_RFCOMM_OPEN_EVT, &evt_data, p_pcb->rfcomm_slot_id);
1482   } else {
1483     evt_data.rfc_close.handle = p_cb->handle;
1484     evt_data.rfc_close.status = BTA_JV_FAILURE;
1485     evt_data.rfc_close.port_status = code;
1486     evt_data.rfc_close.async = true;
1487     if (p_pcb->state == BTA_JV_ST_CL_CLOSING) {
1488       evt_data.rfc_close.async = false;
1489     }
1490     // p_pcb->state = BTA_JV_ST_NONE;
1491     // p_pcb->cong = false;
1492     p_cback = p_cb->p_cback;
1493     p_cback(BTA_JV_RFCOMM_CLOSE_EVT, &evt_data, p_pcb->rfcomm_slot_id);
1494     // bta_jv_free_rfc_cb(p_cb, p_pcb);
1495   }
1496 }
1497 
1498 /*******************************************************************************
1499  *
1500  * Function     bta_jv_port_event_cl_cback
1501  *
1502  * Description  Callback for RFCOMM client port events
1503  *
1504  * Returns      void
1505  *
1506  ******************************************************************************/
bta_jv_port_event_cl_cback(uint32_t code,uint16_t port_handle)1507 static void bta_jv_port_event_cl_cback(uint32_t code, uint16_t port_handle) {
1508   tBTA_JV_RFC_CB* p_cb = bta_jv_rfc_port_to_cb(port_handle);
1509   tBTA_JV_PCB* p_pcb = bta_jv_rfc_port_to_pcb(port_handle);
1510   tBTA_JV evt_data;
1511 
1512   APPL_TRACE_DEBUG("bta_jv_port_event_cl_cback:%d", port_handle);
1513   if (NULL == p_cb || NULL == p_cb->p_cback) return;
1514 
1515   APPL_TRACE_DEBUG(
1516       "bta_jv_port_event_cl_cback code=x%x port_handle:%d handle:%d", code,
1517       port_handle, p_cb->handle);
1518   if (code & PORT_EV_RXCHAR) {
1519     evt_data.data_ind.handle = p_cb->handle;
1520     p_cb->p_cback(BTA_JV_RFCOMM_DATA_IND_EVT, &evt_data, p_pcb->rfcomm_slot_id);
1521   }
1522 
1523   if (code & PORT_EV_FC) {
1524     p_pcb->cong = (code & PORT_EV_FCS) ? false : true;
1525     evt_data.rfc_cong.cong = p_pcb->cong;
1526     evt_data.rfc_cong.handle = p_cb->handle;
1527     evt_data.rfc_cong.status = BTA_JV_SUCCESS;
1528     p_cb->p_cback(BTA_JV_RFCOMM_CONG_EVT, &evt_data, p_pcb->rfcomm_slot_id);
1529   }
1530 
1531   if (code & PORT_EV_TXEMPTY) {
1532     bta_jv_pm_conn_idle(p_pcb->p_pm_cb);
1533   }
1534 }
1535 
1536 /*******************************************************************************
1537  *
1538  * Function     bta_jv_rfcomm_connect
1539  *
1540  * Description  Client initiates an RFCOMM connection
1541  *
1542  * Returns      void
1543  *
1544  ******************************************************************************/
bta_jv_rfcomm_connect(tBTA_JV_MSG * p_data)1545 void bta_jv_rfcomm_connect(tBTA_JV_MSG* p_data) {
1546   uint16_t handle = 0;
1547   uint32_t event_mask = BTA_JV_RFC_EV_MASK;
1548   tPORT_STATE port_state;
1549   uint8_t sec_id = 0;
1550   tBTA_JV_RFC_CB* p_cb = NULL;
1551   tBTA_JV_PCB* p_pcb;
1552   tBTA_JV_API_RFCOMM_CONNECT* cc = &(p_data->rfcomm_connect);
1553   tBTA_JV_RFCOMM_CL_INIT evt_data;
1554 
1555   /* TODO DM role manager
1556   L2CA_SetDesireRole(cc->role);
1557   */
1558 
1559   sec_id = bta_jv_alloc_sec_id();
1560   memset(&evt_data, 0, sizeof(evt_data));
1561   evt_data.sec_id = sec_id;
1562   evt_data.status = BTA_JV_SUCCESS;
1563   if (0 == sec_id ||
1564       BTM_SetSecurityLevel(true, "", sec_id, cc->sec_mask, BT_PSM_RFCOMM,
1565                            BTM_SEC_PROTO_RFCOMM, cc->remote_scn) == false) {
1566     evt_data.status = BTA_JV_FAILURE;
1567     APPL_TRACE_ERROR(
1568         "sec_id:%d is zero or BTM_SetSecurityLevel failed, remote_scn:%d",
1569         sec_id, cc->remote_scn);
1570   }
1571 
1572   if (evt_data.status == BTA_JV_SUCCESS &&
1573       RFCOMM_CreateConnection(UUID_SERVCLASS_SERIAL_PORT, cc->remote_scn, false,
1574                               BTA_JV_DEF_RFC_MTU, cc->peer_bd_addr, &handle,
1575                               bta_jv_port_mgmt_cl_cback) != PORT_SUCCESS) {
1576     APPL_TRACE_ERROR("bta_jv_rfcomm_connect, RFCOMM_CreateConnection failed");
1577     evt_data.status = BTA_JV_FAILURE;
1578   }
1579   if (evt_data.status == BTA_JV_SUCCESS) {
1580     p_cb = bta_jv_alloc_rfc_cb(handle, &p_pcb);
1581     if (p_cb) {
1582       p_cb->p_cback = cc->p_cback;
1583       p_cb->sec_id = sec_id;
1584       p_cb->scn = 0;
1585       p_pcb->state = BTA_JV_ST_CL_OPENING;
1586       p_pcb->rfcomm_slot_id = cc->rfcomm_slot_id;
1587       evt_data.use_co = true;
1588 
1589       PORT_SetEventCallback(handle, bta_jv_port_event_cl_cback);
1590       PORT_SetEventMask(handle, event_mask);
1591       PORT_SetDataCOCallback(handle, bta_jv_port_data_co_cback);
1592 
1593       PORT_GetState(handle, &port_state);
1594 
1595       port_state.fc_type = (PORT_FC_CTS_ON_INPUT | PORT_FC_CTS_ON_OUTPUT);
1596 
1597       PORT_SetState(handle, &port_state);
1598 
1599       evt_data.handle = p_cb->handle;
1600     } else {
1601       evt_data.status = BTA_JV_FAILURE;
1602       APPL_TRACE_ERROR("run out of rfc control block");
1603     }
1604   }
1605   tBTA_JV bta_jv;
1606   bta_jv.rfc_cl_init = evt_data;
1607   cc->p_cback(BTA_JV_RFCOMM_CL_INIT_EVT, &bta_jv, cc->rfcomm_slot_id);
1608   if (bta_jv.rfc_cl_init.status == BTA_JV_FAILURE) {
1609     if (sec_id) bta_jv_free_sec_id(&sec_id);
1610     if (handle) RFCOMM_RemoveConnection(handle);
1611   }
1612 }
1613 
find_rfc_pcb(uint32_t rfcomm_slot_id,tBTA_JV_RFC_CB ** cb,tBTA_JV_PCB ** pcb)1614 static int find_rfc_pcb(uint32_t rfcomm_slot_id, tBTA_JV_RFC_CB** cb,
1615                         tBTA_JV_PCB** pcb) {
1616   *cb = NULL;
1617   *pcb = NULL;
1618   int i;
1619   for (i = 0; i < MAX_RFC_PORTS; i++) {
1620     uint32_t rfc_handle = bta_jv_cb.port_cb[i].handle & BTA_JV_RFC_HDL_MASK;
1621     rfc_handle &= ~BTA_JV_RFCOMM_MASK;
1622     if (rfc_handle && bta_jv_cb.port_cb[i].rfcomm_slot_id == rfcomm_slot_id) {
1623       *pcb = &bta_jv_cb.port_cb[i];
1624       *cb = &bta_jv_cb.rfc_cb[rfc_handle - 1];
1625       APPL_TRACE_DEBUG(
1626           "find_rfc_pcb(): FOUND rfc_cb_handle 0x%x, port.jv_handle:"
1627           " 0x%x, state: %d, rfc_cb->handle: 0x%x",
1628           rfc_handle, (*pcb)->handle, (*pcb)->state, (*cb)->handle);
1629       return 1;
1630     }
1631   }
1632   APPL_TRACE_DEBUG("find_rfc_pcb: cannot find rfc_cb from user data: %u",
1633                    rfcomm_slot_id);
1634   return 0;
1635 }
1636 
1637 /*******************************************************************************
1638  *
1639  * Function     bta_jv_rfcomm_close
1640  *
1641  * Description  Close an RFCOMM connection
1642  *
1643  * Returns      void
1644  *
1645  ******************************************************************************/
bta_jv_rfcomm_close(tBTA_JV_MSG * p_data)1646 void bta_jv_rfcomm_close(tBTA_JV_MSG* p_data) {
1647   tBTA_JV_API_RFCOMM_CLOSE* cc = &(p_data->rfcomm_close);
1648   tBTA_JV_RFC_CB* p_cb = NULL;
1649   tBTA_JV_PCB* p_pcb = NULL;
1650   APPL_TRACE_DEBUG("bta_jv_rfcomm_close, rfc handle:%d", cc->handle);
1651   if (!cc->handle) {
1652     APPL_TRACE_ERROR("bta_jv_rfcomm_close, rfc handle is null");
1653     return;
1654   }
1655 
1656   if (!find_rfc_pcb(cc->rfcomm_slot_id, &p_cb, &p_pcb)) return;
1657   bta_jv_free_rfc_cb(p_cb, p_pcb);
1658   APPL_TRACE_DEBUG("bta_jv_rfcomm_close: sec id in use:%d, rfc_cb in use:%d",
1659                    get_sec_id_used(), get_rfc_cb_used());
1660 }
1661 
1662 /*******************************************************************************
1663  *
1664  * Function     bta_jv_port_mgmt_sr_cback
1665  *
1666  * Description  callback for port mamangement function of rfcomm
1667  *              server connections
1668  *
1669  * Returns      void
1670  *
1671  ******************************************************************************/
bta_jv_port_mgmt_sr_cback(uint32_t code,uint16_t port_handle)1672 static void bta_jv_port_mgmt_sr_cback(uint32_t code, uint16_t port_handle) {
1673   tBTA_JV_PCB* p_pcb = bta_jv_rfc_port_to_pcb(port_handle);
1674   tBTA_JV_RFC_CB* p_cb = bta_jv_rfc_port_to_cb(port_handle);
1675   tBTA_JV evt_data;
1676   RawAddress rem_bda;
1677   uint16_t lcid;
1678   APPL_TRACE_DEBUG("bta_jv_port_mgmt_sr_cback, code:%d, port_handle:%d", code,
1679                    port_handle);
1680   if (NULL == p_cb || NULL == p_cb->p_cback) {
1681     APPL_TRACE_ERROR("bta_jv_port_mgmt_sr_cback, p_cb:%p, p_cb->p_cback%p",
1682                      p_cb, p_cb ? p_cb->p_cback : NULL);
1683     return;
1684   }
1685   uint32_t rfcomm_slot_id = p_pcb->rfcomm_slot_id;
1686   APPL_TRACE_DEBUG(
1687       "bta_jv_port_mgmt_sr_cback code=%d port_handle:0x%x handle:0x%x, "
1688       "p_pcb:%p, user:%d",
1689       code, port_handle, p_cb->handle, p_pcb, p_pcb->rfcomm_slot_id);
1690 
1691   PORT_CheckConnection(port_handle, rem_bda, &lcid);
1692   int failed = true;
1693   if (code == PORT_SUCCESS) {
1694     evt_data.rfc_srv_open.handle = p_pcb->handle;
1695     evt_data.rfc_srv_open.status = BTA_JV_SUCCESS;
1696     evt_data.rfc_srv_open.rem_bda = rem_bda;
1697     tBTA_JV_PCB* p_pcb_new_listen = bta_jv_add_rfc_port(p_cb, p_pcb);
1698     if (p_pcb_new_listen) {
1699       evt_data.rfc_srv_open.new_listen_handle = p_pcb_new_listen->handle;
1700       p_pcb_new_listen->rfcomm_slot_id =
1701           p_cb->p_cback(BTA_JV_RFCOMM_SRV_OPEN_EVT, &evt_data, rfcomm_slot_id);
1702       APPL_TRACE_DEBUG("PORT_SUCCESS: curr_sess:%d, max_sess:%d",
1703                        p_cb->curr_sess, p_cb->max_sess);
1704       failed = false;
1705     } else
1706       APPL_TRACE_ERROR("bta_jv_add_rfc_port failed to create new listen port");
1707   }
1708   if (failed) {
1709     evt_data.rfc_close.handle = p_cb->handle;
1710     evt_data.rfc_close.status = BTA_JV_FAILURE;
1711     evt_data.rfc_close.async = true;
1712     evt_data.rfc_close.port_status = code;
1713     p_pcb->cong = false;
1714 
1715     tBTA_JV_RFCOMM_CBACK* p_cback = p_cb->p_cback;
1716     APPL_TRACE_DEBUG(
1717         "PORT_CLOSED before BTA_JV_RFCOMM_CLOSE_EVT: curr_sess:%d, max_sess:%d",
1718         p_cb->curr_sess, p_cb->max_sess);
1719     if (BTA_JV_ST_SR_CLOSING == p_pcb->state) {
1720       evt_data.rfc_close.async = false;
1721       evt_data.rfc_close.status = BTA_JV_SUCCESS;
1722     }
1723     // p_pcb->state = BTA_JV_ST_NONE;
1724     p_cback(BTA_JV_RFCOMM_CLOSE_EVT, &evt_data, rfcomm_slot_id);
1725     // bta_jv_free_rfc_cb(p_cb, p_pcb);
1726 
1727     APPL_TRACE_DEBUG(
1728         "PORT_CLOSED after BTA_JV_RFCOMM_CLOSE_EVT: curr_sess:%d, max_sess:%d",
1729         p_cb->curr_sess, p_cb->max_sess);
1730   }
1731 }
1732 
1733 /*******************************************************************************
1734  *
1735  * Function     bta_jv_port_event_sr_cback
1736  *
1737  * Description  Callback for RFCOMM server port events
1738  *
1739  * Returns      void
1740  *
1741  ******************************************************************************/
bta_jv_port_event_sr_cback(uint32_t code,uint16_t port_handle)1742 static void bta_jv_port_event_sr_cback(uint32_t code, uint16_t port_handle) {
1743   tBTA_JV_PCB* p_pcb = bta_jv_rfc_port_to_pcb(port_handle);
1744   tBTA_JV_RFC_CB* p_cb = bta_jv_rfc_port_to_cb(port_handle);
1745   tBTA_JV evt_data;
1746 
1747   if (NULL == p_cb || NULL == p_cb->p_cback) return;
1748 
1749   APPL_TRACE_DEBUG(
1750       "bta_jv_port_event_sr_cback code=x%x port_handle:%d handle:%d", code,
1751       port_handle, p_cb->handle);
1752 
1753   uint32_t user_data = p_pcb->rfcomm_slot_id;
1754   if (code & PORT_EV_RXCHAR) {
1755     evt_data.data_ind.handle = p_cb->handle;
1756     p_cb->p_cback(BTA_JV_RFCOMM_DATA_IND_EVT, &evt_data, user_data);
1757   }
1758 
1759   if (code & PORT_EV_FC) {
1760     p_pcb->cong = (code & PORT_EV_FCS) ? false : true;
1761     evt_data.rfc_cong.cong = p_pcb->cong;
1762     evt_data.rfc_cong.handle = p_cb->handle;
1763     evt_data.rfc_cong.status = BTA_JV_SUCCESS;
1764     p_cb->p_cback(BTA_JV_RFCOMM_CONG_EVT, &evt_data, user_data);
1765   }
1766 
1767   if (code & PORT_EV_TXEMPTY) {
1768     bta_jv_pm_conn_idle(p_pcb->p_pm_cb);
1769   }
1770 }
1771 
1772 /*******************************************************************************
1773  *
1774  * Function     bta_jv_add_rfc_port
1775  *
1776  * Description  add a port for server when the existing posts is open
1777  *
1778  * Returns   return a pointer to tBTA_JV_PCB just added
1779  *
1780  ******************************************************************************/
bta_jv_add_rfc_port(tBTA_JV_RFC_CB * p_cb,tBTA_JV_PCB * p_pcb_open)1781 static tBTA_JV_PCB* bta_jv_add_rfc_port(tBTA_JV_RFC_CB* p_cb,
1782                                         tBTA_JV_PCB* p_pcb_open) {
1783   uint8_t used = 0, i, listen = 0;
1784   uint32_t si = 0;
1785   tPORT_STATE port_state;
1786   uint32_t event_mask = BTA_JV_RFC_EV_MASK;
1787   tBTA_JV_PCB* p_pcb = NULL;
1788   if (p_cb->max_sess > 1) {
1789     for (i = 0; i < p_cb->max_sess; i++) {
1790       if (p_cb->rfc_hdl[i] != 0) {
1791         p_pcb = &bta_jv_cb.port_cb[p_cb->rfc_hdl[i] - 1];
1792         if (p_pcb->state == BTA_JV_ST_SR_LISTEN) {
1793           listen++;
1794           if (p_pcb_open == p_pcb) {
1795             APPL_TRACE_DEBUG(
1796                 "bta_jv_add_rfc_port, port_handle:%d, change the listen port "
1797                 "to open state",
1798                 p_pcb->port_handle);
1799             p_pcb->state = BTA_JV_ST_SR_OPEN;
1800 
1801           } else {
1802             APPL_TRACE_ERROR(
1803                 "bta_jv_add_rfc_port, open pcb not matching listen one,"
1804                 "listen count:%d, listen pcb handle:%d, open pcb:%d",
1805                 listen, p_pcb->port_handle, p_pcb_open->handle);
1806             return NULL;
1807           }
1808         }
1809         used++;
1810       } else if (si == 0) {
1811         si = i + 1;
1812       }
1813     }
1814 
1815     APPL_TRACE_DEBUG(
1816         "bta_jv_add_rfc_port max_sess=%d used:%d curr_sess:%d, listen:%d si:%d",
1817         p_cb->max_sess, used, p_cb->curr_sess, listen, si);
1818     if (used < p_cb->max_sess && listen == 1 && si) {
1819       si--;
1820       if (RFCOMM_CreateConnection(p_cb->sec_id, p_cb->scn, true,
1821                                   BTA_JV_DEF_RFC_MTU, RawAddress::kAny,
1822                                   &(p_cb->rfc_hdl[si]),
1823                                   bta_jv_port_mgmt_sr_cback) == PORT_SUCCESS) {
1824         p_cb->curr_sess++;
1825         p_pcb = &bta_jv_cb.port_cb[p_cb->rfc_hdl[si] - 1];
1826         p_pcb->state = BTA_JV_ST_SR_LISTEN;
1827         p_pcb->port_handle = p_cb->rfc_hdl[si];
1828         p_pcb->rfcomm_slot_id = p_pcb_open->rfcomm_slot_id;
1829 
1830         PORT_ClearKeepHandleFlag(p_pcb->port_handle);
1831         PORT_SetEventCallback(p_pcb->port_handle, bta_jv_port_event_sr_cback);
1832         PORT_SetDataCOCallback(p_pcb->port_handle, bta_jv_port_data_co_cback);
1833         PORT_SetEventMask(p_pcb->port_handle, event_mask);
1834         PORT_GetState(p_pcb->port_handle, &port_state);
1835 
1836         port_state.fc_type = (PORT_FC_CTS_ON_INPUT | PORT_FC_CTS_ON_OUTPUT);
1837 
1838         PORT_SetState(p_pcb->port_handle, &port_state);
1839         p_pcb->handle = BTA_JV_RFC_H_S_TO_HDL(p_cb->handle, si);
1840         APPL_TRACE_DEBUG(
1841             "bta_jv_add_rfc_port: p_pcb->handle:0x%x, curr_sess:%d",
1842             p_pcb->handle, p_cb->curr_sess);
1843       }
1844     } else
1845       APPL_TRACE_ERROR(
1846           "bta_jv_add_rfc_port, cannot create new rfc listen port");
1847   }
1848   APPL_TRACE_DEBUG("bta_jv_add_rfc_port: sec id in use:%d, rfc_cb in use:%d",
1849                    get_sec_id_used(), get_rfc_cb_used());
1850   return p_pcb;
1851 }
1852 
1853 /*******************************************************************************
1854  *
1855  * Function     bta_jv_rfcomm_start_server
1856  *
1857  * Description  waits for an RFCOMM client to connect
1858  *
1859  *
1860  * Returns      void
1861  *
1862  ******************************************************************************/
bta_jv_rfcomm_start_server(tBTA_JV_MSG * p_data)1863 void bta_jv_rfcomm_start_server(tBTA_JV_MSG* p_data) {
1864   uint16_t handle = 0;
1865   uint32_t event_mask = BTA_JV_RFC_EV_MASK;
1866   tPORT_STATE port_state;
1867   uint8_t sec_id = 0;
1868   tBTA_JV_RFC_CB* p_cb = NULL;
1869   tBTA_JV_PCB* p_pcb;
1870   tBTA_JV_API_RFCOMM_SERVER* rs = &(p_data->rfcomm_server);
1871   tBTA_JV_RFCOMM_START evt_data;
1872 
1873   /* TODO DM role manager
1874   L2CA_SetDesireRole(rs->role);
1875   */
1876   memset(&evt_data, 0, sizeof(evt_data));
1877   evt_data.status = BTA_JV_FAILURE;
1878   APPL_TRACE_DEBUG(
1879       "bta_jv_rfcomm_start_server: sec id in use:%d, rfc_cb in use:%d",
1880       get_sec_id_used(), get_rfc_cb_used());
1881 
1882   do {
1883     sec_id = bta_jv_alloc_sec_id();
1884 
1885     if (0 == sec_id ||
1886         BTM_SetSecurityLevel(false, "JV PORT", sec_id, rs->sec_mask,
1887                              BT_PSM_RFCOMM, BTM_SEC_PROTO_RFCOMM,
1888                              rs->local_scn) == false) {
1889       APPL_TRACE_ERROR("bta_jv_rfcomm_start_server, run out of sec_id");
1890       break;
1891     }
1892 
1893     if (RFCOMM_CreateConnection(sec_id, rs->local_scn, true, BTA_JV_DEF_RFC_MTU,
1894                                 RawAddress::kAny, &handle,
1895                                 bta_jv_port_mgmt_sr_cback) != PORT_SUCCESS) {
1896       APPL_TRACE_ERROR(
1897           "bta_jv_rfcomm_start_server, RFCOMM_CreateConnection failed");
1898       break;
1899     }
1900 
1901     p_cb = bta_jv_alloc_rfc_cb(handle, &p_pcb);
1902     if (!p_cb) {
1903       APPL_TRACE_ERROR(
1904           "bta_jv_rfcomm_start_server, run out of rfc control block");
1905       break;
1906     }
1907 
1908     p_cb->max_sess = rs->max_session;
1909     p_cb->p_cback = rs->p_cback;
1910     p_cb->sec_id = sec_id;
1911     p_cb->scn = rs->local_scn;
1912     p_pcb->state = BTA_JV_ST_SR_LISTEN;
1913     p_pcb->rfcomm_slot_id = rs->rfcomm_slot_id;
1914     evt_data.status = BTA_JV_SUCCESS;
1915     evt_data.handle = p_cb->handle;
1916     evt_data.sec_id = sec_id;
1917     evt_data.use_co = true;
1918 
1919     PORT_ClearKeepHandleFlag(handle);
1920     PORT_SetEventCallback(handle, bta_jv_port_event_sr_cback);
1921     PORT_SetEventMask(handle, event_mask);
1922     PORT_GetState(handle, &port_state);
1923 
1924     port_state.fc_type = (PORT_FC_CTS_ON_INPUT | PORT_FC_CTS_ON_OUTPUT);
1925 
1926     PORT_SetState(handle, &port_state);
1927   } while (0);
1928 
1929   tBTA_JV bta_jv;
1930   bta_jv.rfc_start = evt_data;
1931   rs->p_cback(BTA_JV_RFCOMM_START_EVT, &bta_jv, rs->rfcomm_slot_id);
1932   if (bta_jv.rfc_start.status == BTA_JV_SUCCESS) {
1933     PORT_SetDataCOCallback(handle, bta_jv_port_data_co_cback);
1934   } else {
1935     if (sec_id) bta_jv_free_sec_id(&sec_id);
1936     if (handle) RFCOMM_RemoveConnection(handle);
1937   }
1938 }
1939 
1940 /*******************************************************************************
1941  *
1942  * Function     bta_jv_rfcomm_stop_server
1943  *
1944  * Description  stops an RFCOMM server
1945  *
1946  * Returns      void
1947  *
1948  ******************************************************************************/
1949 
bta_jv_rfcomm_stop_server(tBTA_JV_MSG * p_data)1950 void bta_jv_rfcomm_stop_server(tBTA_JV_MSG* p_data) {
1951   tBTA_JV_API_RFCOMM_SERVER* ls = &(p_data->rfcomm_server);
1952   tBTA_JV_RFC_CB* p_cb = NULL;
1953   tBTA_JV_PCB* p_pcb = NULL;
1954   APPL_TRACE_DEBUG("bta_jv_rfcomm_stop_server");
1955   if (!ls->handle) {
1956     APPL_TRACE_ERROR("bta_jv_rfcomm_stop_server, jv handle is null");
1957     return;
1958   }
1959 
1960   if (!find_rfc_pcb(ls->rfcomm_slot_id, &p_cb, &p_pcb)) return;
1961   APPL_TRACE_DEBUG("bta_jv_rfcomm_stop_server: p_pcb:%p, p_pcb->port_handle:%d",
1962                    p_pcb, p_pcb->port_handle);
1963   bta_jv_free_rfc_cb(p_cb, p_pcb);
1964   APPL_TRACE_DEBUG(
1965       "bta_jv_rfcomm_stop_server: sec id in use:%d, rfc_cb in use:%d",
1966       get_sec_id_used(), get_rfc_cb_used());
1967 }
1968 
1969 /*******************************************************************************
1970  *
1971  * Function     bta_jv_rfcomm_write
1972  *
1973  * Description  write data to an RFCOMM connection
1974  *
1975  * Returns      void
1976  *
1977  ******************************************************************************/
bta_jv_rfcomm_write(tBTA_JV_MSG * p_data)1978 void bta_jv_rfcomm_write(tBTA_JV_MSG* p_data) {
1979   tBTA_JV_API_RFCOMM_WRITE* wc = &(p_data->rfcomm_write);
1980   tBTA_JV_RFC_CB* p_cb = wc->p_cb;
1981   tBTA_JV_PCB* p_pcb = wc->p_pcb;
1982 
1983   if (p_pcb->state == BTA_JV_ST_NONE) {
1984     APPL_TRACE_ERROR("%s in state BTA_JV_ST_NONE - cannot write", __func__);
1985     return;
1986   }
1987 
1988   tBTA_JV_RFCOMM_WRITE evt_data;
1989   evt_data.status = BTA_JV_FAILURE;
1990   evt_data.handle = p_cb->handle;
1991   evt_data.req_id = wc->req_id;
1992   evt_data.cong = p_pcb->cong;
1993   evt_data.len = 0;
1994 
1995   bta_jv_pm_conn_busy(p_pcb->p_pm_cb);
1996 
1997   if (!evt_data.cong &&
1998       PORT_WriteDataCO(p_pcb->port_handle, &evt_data.len) == PORT_SUCCESS) {
1999     evt_data.status = BTA_JV_SUCCESS;
2000   }
2001 
2002   // Update congestion flag
2003   evt_data.cong = p_pcb->cong;
2004 
2005   if (p_cb->p_cback) {
2006     tBTA_JV bta_jv;
2007     bta_jv.rfc_write = evt_data;
2008     p_cb->p_cback(BTA_JV_RFCOMM_WRITE_EVT, &bta_jv, p_pcb->rfcomm_slot_id);
2009   } else {
2010     APPL_TRACE_ERROR("%s No JV callback set", __func__);
2011   }
2012 }
2013 
2014 /*******************************************************************************
2015  *
2016  * Function     bta_jv_set_pm_profile
2017  *
2018  * Description  Set or free power mode profile for a JV application
2019  *
2020  * Returns      void
2021  *
2022  ******************************************************************************/
bta_jv_set_pm_profile(tBTA_JV_MSG * p_data)2023 void bta_jv_set_pm_profile(tBTA_JV_MSG* p_data) {
2024   tBTA_JV_STATUS status;
2025   tBTA_JV_PM_CB* p_cb;
2026 
2027   APPL_TRACE_API("bta_jv_set_pm_profile(handle: 0x%x, app_id: %d, init_st: %d)",
2028                  p_data->set_pm.handle, p_data->set_pm.app_id,
2029                  p_data->set_pm.init_st);
2030 
2031   /* clear PM control block */
2032   if (p_data->set_pm.app_id == BTA_JV_PM_ID_CLEAR) {
2033     status = bta_jv_free_set_pm_profile_cb(p_data->set_pm.handle);
2034 
2035     if (status != BTA_JV_SUCCESS) {
2036       APPL_TRACE_WARNING("bta_jv_set_pm_profile() free pm cb failed: reason %d",
2037                          status);
2038     }
2039   } else /* set PM control block */
2040   {
2041     p_cb = bta_jv_alloc_set_pm_profile_cb(p_data->set_pm.handle,
2042                                           p_data->set_pm.app_id);
2043 
2044     if (NULL != p_cb)
2045       bta_jv_pm_state_change(p_cb, p_data->set_pm.init_st);
2046     else
2047       APPL_TRACE_WARNING("bta_jv_alloc_set_pm_profile_cb() failed");
2048   }
2049 }
2050 
2051 /*******************************************************************************
2052  *
2053  * Function     bta_jv_change_pm_state
2054  *
2055  * Description  change jv pm connect state, used internally
2056  *
2057  * Returns      void
2058  *
2059  ******************************************************************************/
bta_jv_change_pm_state(tBTA_JV_MSG * p_data)2060 void bta_jv_change_pm_state(tBTA_JV_MSG* p_data) {
2061   tBTA_JV_API_PM_STATE_CHANGE* p_msg = (tBTA_JV_API_PM_STATE_CHANGE*)p_data;
2062 
2063   if (p_msg->p_cb) bta_jv_pm_state_change(p_msg->p_cb, p_msg->state);
2064 }
2065 
2066 /*******************************************************************************
2067  *
2068  * Function    bta_jv_set_pm_conn_state
2069  *
2070  * Description Send pm event state change to jv state machine to serialize jv pm
2071  *             changes in relation to other jv messages. internal API use
2072  *             mainly.
2073  *
2074  * Params:     p_cb: jv pm control block, NULL pointer returns failure
2075  *             new_state: new PM connections state, setting is forced by action
2076  *                        function
2077  *
2078  * Returns     BTA_JV_SUCCESS, BTA_JV_FAILURE (buffer allocation, or NULL ptr!)
2079  *
2080  ******************************************************************************/
bta_jv_set_pm_conn_state(tBTA_JV_PM_CB * p_cb,const tBTA_JV_CONN_STATE new_st)2081 tBTA_JV_STATUS bta_jv_set_pm_conn_state(tBTA_JV_PM_CB* p_cb,
2082                                         const tBTA_JV_CONN_STATE new_st) {
2083   if (p_cb == NULL) return BTA_JV_FAILURE;
2084 
2085   APPL_TRACE_API("%s: handle:0x%x, state: %d", __func__, p_cb->handle, new_st);
2086 
2087   tBTA_JV_API_PM_STATE_CHANGE* p_msg = (tBTA_JV_API_PM_STATE_CHANGE*)osi_malloc(
2088       sizeof(tBTA_JV_API_PM_STATE_CHANGE));
2089   p_msg->hdr.event = BTA_JV_API_PM_STATE_CHANGE_EVT;
2090   p_msg->p_cb = p_cb;
2091   p_msg->state = new_st;
2092 
2093   bta_sys_sendmsg(p_msg);
2094 
2095   return BTA_JV_SUCCESS;
2096 }
2097 
2098 /*******************************************************************************
2099  *
2100  * Function    bta_jv_pm_conn_busy
2101  *
2102  * Description set pm connection busy state (input param safe)
2103  *
2104  * Params      p_cb: pm control block of jv connection
2105  *
2106  * Returns     void
2107  *
2108  ******************************************************************************/
bta_jv_pm_conn_busy(tBTA_JV_PM_CB * p_cb)2109 static void bta_jv_pm_conn_busy(tBTA_JV_PM_CB* p_cb) {
2110   if ((NULL != p_cb) && (BTA_JV_PM_IDLE_ST == p_cb->state))
2111     bta_jv_pm_state_change(p_cb, BTA_JV_CONN_BUSY);
2112 }
2113 
2114 /*******************************************************************************
2115  *
2116  * Function    bta_jv_pm_conn_busy
2117  *
2118  * Description set pm connection busy state (input param safe)
2119  *
2120  * Params      p_cb: pm control block of jv connection
2121  *
2122  * Returns     void
2123  *
2124  ******************************************************************************/
bta_jv_pm_conn_idle(tBTA_JV_PM_CB * p_cb)2125 static void bta_jv_pm_conn_idle(tBTA_JV_PM_CB* p_cb) {
2126   if ((NULL != p_cb) && (BTA_JV_PM_IDLE_ST != p_cb->state))
2127     bta_jv_pm_state_change(p_cb, BTA_JV_CONN_IDLE);
2128 }
2129 
2130 /*******************************************************************************
2131  *
2132  * Function     bta_jv_pm_state_change
2133  *
2134  * Description  Notify power manager there is state change
2135  *
2136  * Params      p_cb: must be NONE NULL
2137  *
2138  * Returns      void
2139  *
2140  ******************************************************************************/
bta_jv_pm_state_change(tBTA_JV_PM_CB * p_cb,const tBTA_JV_CONN_STATE state)2141 static void bta_jv_pm_state_change(tBTA_JV_PM_CB* p_cb,
2142                                    const tBTA_JV_CONN_STATE state) {
2143   APPL_TRACE_API(
2144       "bta_jv_pm_state_change(p_cb: 0x%x, handle: 0x%x, busy/idle_state: %d"
2145       ", app_id: %d, conn_state: %d)",
2146       p_cb, p_cb->handle, p_cb->state, p_cb->app_id, state);
2147 
2148   switch (state) {
2149     case BTA_JV_CONN_OPEN:
2150       bta_sys_conn_open(BTA_ID_JV, p_cb->app_id, p_cb->peer_bd_addr);
2151       break;
2152 
2153     case BTA_JV_CONN_CLOSE:
2154       bta_sys_conn_close(BTA_ID_JV, p_cb->app_id, p_cb->peer_bd_addr);
2155       break;
2156 
2157     case BTA_JV_APP_OPEN:
2158       bta_sys_app_open(BTA_ID_JV, p_cb->app_id, p_cb->peer_bd_addr);
2159       break;
2160 
2161     case BTA_JV_APP_CLOSE:
2162       bta_sys_app_close(BTA_ID_JV, p_cb->app_id, p_cb->peer_bd_addr);
2163       break;
2164 
2165     case BTA_JV_SCO_OPEN:
2166       bta_sys_sco_open(BTA_ID_JV, p_cb->app_id, p_cb->peer_bd_addr);
2167       break;
2168 
2169     case BTA_JV_SCO_CLOSE:
2170       bta_sys_sco_close(BTA_ID_JV, p_cb->app_id, p_cb->peer_bd_addr);
2171       break;
2172 
2173     case BTA_JV_CONN_IDLE:
2174       p_cb->state = BTA_JV_PM_IDLE_ST;
2175       bta_sys_idle(BTA_ID_JV, p_cb->app_id, p_cb->peer_bd_addr);
2176       break;
2177 
2178     case BTA_JV_CONN_BUSY:
2179       p_cb->state = BTA_JV_PM_BUSY_ST;
2180       bta_sys_busy(BTA_ID_JV, p_cb->app_id, p_cb->peer_bd_addr);
2181       break;
2182 
2183     default:
2184       APPL_TRACE_WARNING("bta_jv_pm_state_change(state: %d): Invalid state",
2185                          state);
2186       break;
2187   }
2188 }
2189 /******************************************************************************/
2190 
fcchan_get(uint16_t chan,char create)2191 static struct fc_channel* fcchan_get(uint16_t chan, char create) {
2192   struct fc_channel* t = fc_channels;
2193   static tL2CAP_FIXED_CHNL_REG fcr = {
2194       .pL2CA_FixedConn_Cb = fcchan_conn_chng_cbk,
2195       .pL2CA_FixedData_Cb = fcchan_data_cbk,
2196       .default_idle_tout = 0xffff,
2197       .fixed_chnl_opts =
2198           {
2199               .mode = L2CAP_FCR_BASIC_MODE,
2200               .max_transmit = 0xFF,
2201               .rtrans_tout = 2000,
2202               .mon_tout = 12000,
2203               .mps = 670,
2204               .tx_win_sz = 1,
2205           },
2206   };
2207 
2208   while (t && t->chan != chan) t = t->next;
2209 
2210   if (t)
2211     return t;
2212   else if (!create)
2213     return NULL; /* we cannot alloc a struct if not asked to */
2214 
2215   t = static_cast<struct fc_channel*>(osi_calloc(sizeof(*t)));
2216   t->chan = chan;
2217 
2218   if (!L2CA_RegisterFixedChannel(chan, &fcr)) {
2219     osi_free(t);
2220     return NULL;
2221   }
2222 
2223   // link it in
2224   t->next = fc_channels;
2225   fc_channels = t;
2226 
2227   return t;
2228 }
2229 
2230 /* pass NULL to find servers */
fcclient_find_by_addr(struct fc_client * start,const RawAddress * addr)2231 static struct fc_client* fcclient_find_by_addr(struct fc_client* start,
2232                                                const RawAddress* addr) {
2233   struct fc_client* t = start;
2234 
2235   while (t) {
2236     /* match client if have addr */
2237     if (addr && addr == &t->remote_addr) break;
2238 
2239     /* match server if do not have addr */
2240     if (!addr && t->server) break;
2241 
2242     t = t->next_all_list;
2243   }
2244 
2245   return t;
2246 }
2247 
fcclient_find_by_id(uint32_t id)2248 static struct fc_client* fcclient_find_by_id(uint32_t id) {
2249   struct fc_client* t = fc_clients;
2250 
2251   while (t && t->id != id) t = t->next_all_list;
2252 
2253   return t;
2254 }
2255 
fcclient_alloc(uint16_t chan,char server,const uint8_t * sec_id_to_use)2256 static struct fc_client* fcclient_alloc(uint16_t chan, char server,
2257                                         const uint8_t* sec_id_to_use) {
2258   struct fc_channel* fc = fcchan_get(chan, true);
2259   struct fc_client* t;
2260   uint8_t sec_id;
2261 
2262   if (!fc) return NULL;
2263 
2264   if (fc->has_server && server)
2265     return NULL; /* no way to have multiple servers on same channel */
2266 
2267   if (sec_id_to_use)
2268     sec_id = *sec_id_to_use;
2269   else
2270     sec_id = bta_jv_alloc_sec_id();
2271 
2272   t = static_cast<fc_client*>(osi_calloc(sizeof(*t)));
2273   // Allocate it a unique ID
2274   do {
2275     t->id = ++fc_next_id;
2276   } while (!t->id || fcclient_find_by_id(t->id));
2277 
2278   // Populate some params
2279   t->chan = chan;
2280   t->server = server;
2281 
2282   // Get a security id
2283   t->sec_id = sec_id;
2284 
2285   // Link it in to global list
2286   t->next_all_list = fc_clients;
2287   fc_clients = t;
2288 
2289   // Link it in to channel list
2290   t->next_chan_list = fc->clients;
2291   fc->clients = t;
2292 
2293   // Update channel if needed
2294   if (server) fc->has_server = true;
2295 
2296   return t;
2297 }
2298 
fcclient_free(struct fc_client * fc)2299 static void fcclient_free(struct fc_client* fc) {
2300   struct fc_client* t = fc_clients;
2301   struct fc_channel* tc = fcchan_get(fc->chan, false);
2302 
2303   // remove from global list
2304   while (t && t->next_all_list != fc) t = t->next_all_list;
2305 
2306   if (!t && fc != fc_clients) return; /* prevent double-free */
2307 
2308   if (t)
2309     t->next_all_list = fc->next_all_list;
2310   else
2311     fc_clients = fc->next_all_list;
2312 
2313   // remove from channel list
2314   if (tc) {
2315     t = tc->clients;
2316 
2317     while (t && t->next_chan_list != fc) t = t->next_chan_list;
2318 
2319     if (t)
2320       t->next_chan_list = fc->next_chan_list;
2321     else
2322       tc->clients = fc->next_chan_list;
2323 
2324     // if was server then channel no longer has a server
2325     if (fc->server) tc->has_server = false;
2326   }
2327 
2328   // free security id
2329   bta_jv_free_sec_id(&fc->sec_id);
2330 
2331   osi_free(fc);
2332 }
2333 
fcchan_conn_chng_cbk(uint16_t chan,const RawAddress & bd_addr,bool connected,uint16_t reason,tBT_TRANSPORT transport)2334 static void fcchan_conn_chng_cbk(uint16_t chan, const RawAddress& bd_addr,
2335                                  bool connected, uint16_t reason,
2336                                  tBT_TRANSPORT transport) {
2337   tBTA_JV init_evt;
2338   tBTA_JV open_evt;
2339   struct fc_channel* tc;
2340   struct fc_client *t = NULL, *new_conn;
2341   tBTA_JV_L2CAP_CBACK* p_cback = NULL;
2342   char call_init = false;
2343   uint32_t l2cap_socket_id;
2344 
2345   tc = fcchan_get(chan, false);
2346   if (tc) {
2347     t = fcclient_find_by_addr(
2348         tc->clients,
2349         &bd_addr);  // try to find an open socked for that addr
2350     if (t) {
2351       p_cback = t->p_cback;
2352       l2cap_socket_id = t->l2cap_socket_id;
2353     } else {
2354       t = fcclient_find_by_addr(
2355           tc->clients,
2356           NULL);  // try to find a listening socked for that channel
2357       if (t) {
2358         // found: create a normal connection socket and assign the connection to
2359         // it
2360         new_conn = fcclient_alloc(chan, false, &t->sec_id);
2361         if (new_conn) {
2362           new_conn->remote_addr = bd_addr;
2363           new_conn->p_cback = NULL;     // for now
2364           new_conn->init_called = true; /*nop need to do it again */
2365 
2366           p_cback = t->p_cback;
2367           l2cap_socket_id = t->l2cap_socket_id;
2368 
2369           t = new_conn;
2370         }
2371       } else {
2372         // drop it
2373         return;
2374       }
2375     }
2376   }
2377 
2378   if (t) {
2379     if (!t->init_called) {
2380       call_init = true;
2381       t->init_called = true;
2382 
2383       init_evt.l2c_cl_init.handle = t->id;
2384       init_evt.l2c_cl_init.status = BTA_JV_SUCCESS;
2385       init_evt.l2c_cl_init.sec_id = t->sec_id;
2386     }
2387 
2388     open_evt.l2c_open.handle = t->id;
2389     open_evt.l2c_open.tx_mtu = 23; /* 23, why not ?*/
2390     memcpy(&open_evt.l2c_le_open.rem_bda, &t->remote_addr,
2391            sizeof(open_evt.l2c_le_open.rem_bda));
2392     // TODO: (apanicke) Change the way these functions work so that casting
2393     // isn't needed
2394     open_evt.l2c_le_open.p_p_cback = (void**)&t->p_cback;
2395     open_evt.l2c_le_open.p_user_data = (void**)&t->l2cap_socket_id;
2396     open_evt.l2c_le_open.status = BTA_JV_SUCCESS;
2397 
2398     if (connected) {
2399       open_evt.l2c_open.status = BTA_JV_SUCCESS;
2400     } else {
2401       fcclient_free(t);
2402       open_evt.l2c_open.status = BTA_JV_FAILURE;
2403     }
2404   }
2405 
2406   if (call_init) p_cback(BTA_JV_L2CAP_CL_INIT_EVT, &init_evt, l2cap_socket_id);
2407 
2408   // call this with lock taken so socket does not disappear from under us */
2409   if (p_cback) {
2410     p_cback(BTA_JV_L2CAP_OPEN_EVT, &open_evt, l2cap_socket_id);
2411     if (!t->p_cback) /* no callback set, means they do not want this one... */
2412       fcclient_free(t);
2413   }
2414 }
2415 
fcchan_data_cbk(uint16_t chan,const RawAddress & bd_addr,BT_HDR * p_buf)2416 static void fcchan_data_cbk(uint16_t chan, const RawAddress& bd_addr,
2417                             BT_HDR* p_buf) {
2418   tBTA_JV evt_data;
2419   struct fc_channel* tc;
2420   struct fc_client* t = NULL;
2421   tBTA_JV_L2CAP_CBACK* sock_cback = NULL;
2422   uint32_t sock_id;
2423 
2424   tc = fcchan_get(chan, false);
2425   if (tc) {
2426     // try to find an open socked for that addr and channel
2427     t = fcclient_find_by_addr(tc->clients, &bd_addr);
2428     if (!t) {
2429       // no socket -> drop it
2430       return;
2431     }
2432   }
2433 
2434   sock_cback = t->p_cback;
2435   sock_id = t->l2cap_socket_id;
2436   evt_data.le_data_ind.handle = t->id;
2437   evt_data.le_data_ind.p_buf = p_buf;
2438 
2439   if (sock_cback) sock_cback(BTA_JV_L2CAP_DATA_IND_EVT, &evt_data, sock_id);
2440 }
2441 
2442 /*******************************************************************************
2443  *
2444  * Function     bta_jv_l2cap_connect_le
2445  *
2446  * Description  makes an le l2cap client connection
2447  *
2448  * Returns      void
2449  *
2450  ******************************************************************************/
bta_jv_l2cap_connect_le(tBTA_JV_MSG * p_data)2451 void bta_jv_l2cap_connect_le(tBTA_JV_MSG* p_data) {
2452   tBTA_JV_API_L2CAP_CONNECT* cc = &(p_data->l2cap_connect);
2453   tBTA_JV evt;
2454   uint32_t id;
2455   char call_init_f = true;
2456   struct fc_client* t;
2457 
2458   evt.l2c_cl_init.handle = GAP_INVALID_HANDLE;
2459   evt.l2c_cl_init.status = BTA_JV_FAILURE;
2460 
2461   t = fcclient_alloc(cc->remote_chan, false, NULL);
2462   if (!t) {
2463     cc->p_cback(BTA_JV_L2CAP_CL_INIT_EVT, &evt, cc->l2cap_socket_id);
2464     return;
2465   }
2466 
2467   t->p_cback = cc->p_cback;
2468   t->l2cap_socket_id = cc->l2cap_socket_id;
2469   t->remote_addr = cc->peer_bd_addr;
2470   id = t->id;
2471   t->init_called = false;
2472 
2473   if (L2CA_ConnectFixedChnl(t->chan, t->remote_addr)) {
2474     evt.l2c_cl_init.status = BTA_JV_SUCCESS;
2475     evt.l2c_cl_init.handle = id;
2476   }
2477 
2478   // it could have been deleted/moved from under us, so re-find it */
2479   t = fcclient_find_by_id(id);
2480   if (t) {
2481     if (evt.l2c_cl_init.status == BTA_JV_SUCCESS)
2482       call_init_f = !t->init_called;
2483     else
2484       fcclient_free(t);
2485   }
2486   if (call_init_f)
2487     cc->p_cback(BTA_JV_L2CAP_CL_INIT_EVT, &evt, cc->l2cap_socket_id);
2488   t->init_called = true;
2489 }
2490 
2491 /*******************************************************************************
2492  *
2493  * Function     bta_jv_l2cap_stop_server_le
2494  *
2495  * Description  stops an LE L2CAP server
2496  *
2497  * Returns      void
2498  *
2499  ******************************************************************************/
bta_jv_l2cap_stop_server_le(tBTA_JV_MSG * p_data)2500 void bta_jv_l2cap_stop_server_le(tBTA_JV_MSG* p_data) {
2501   tBTA_JV evt;
2502   tBTA_JV_API_L2CAP_SERVER* ls = &(p_data->l2cap_server);
2503   tBTA_JV_L2CAP_CBACK* p_cback = NULL;
2504   struct fc_channel* fcchan;
2505   struct fc_client* fcclient;
2506   uint32_t l2cap_socket_id;
2507 
2508   evt.l2c_close.status = BTA_JV_FAILURE;
2509   evt.l2c_close.async = false;
2510   evt.l2c_close.handle = GAP_INVALID_HANDLE;
2511 
2512   fcchan = fcchan_get(ls->local_chan, false);
2513   if (fcchan) {
2514     while ((fcclient = fcchan->clients)) {
2515       p_cback = fcclient->p_cback;
2516       l2cap_socket_id = fcclient->l2cap_socket_id;
2517 
2518       evt.l2c_close.handle = fcclient->id;
2519       evt.l2c_close.status = BTA_JV_SUCCESS;
2520       evt.l2c_close.async = false;
2521 
2522       fcclient_free(fcclient);
2523 
2524       if (p_cback) p_cback(BTA_JV_L2CAP_CLOSE_EVT, &evt, l2cap_socket_id);
2525     }
2526   }
2527 }
2528 
2529 /*******************************************************************************
2530  *
2531  * Function     bta_jv_l2cap_start_server_le
2532  *
2533  * Description  starts an LE L2CAP server
2534  *
2535  * Returns      void
2536  *
2537  ******************************************************************************/
bta_jv_l2cap_start_server_le(tBTA_JV_MSG * p_data)2538 void bta_jv_l2cap_start_server_le(tBTA_JV_MSG* p_data) {
2539   tBTA_JV_API_L2CAP_SERVER* ss = &(p_data->l2cap_server);
2540   tBTA_JV_L2CAP_START evt_data;
2541   struct fc_client* t;
2542 
2543   evt_data.handle = GAP_INVALID_HANDLE;
2544   evt_data.status = BTA_JV_FAILURE;
2545 
2546   t = fcclient_alloc(ss->local_chan, true, NULL);
2547   if (!t) goto out;
2548 
2549   t->p_cback = ss->p_cback;
2550   t->l2cap_socket_id = ss->l2cap_socket_id;
2551 
2552   // if we got here, we're registered...
2553   evt_data.status = BTA_JV_SUCCESS;
2554   evt_data.handle = t->id;
2555   evt_data.sec_id = t->sec_id;
2556 
2557 out:
2558   tBTA_JV bta_jv;
2559   bta_jv.l2c_start = evt_data;
2560   ss->p_cback(BTA_JV_L2CAP_START_EVT, &bta_jv, ss->l2cap_socket_id);
2561 }
2562 
2563 /*******************************************************************************
2564  *
2565  * Function     bta_jv_l2cap_close_fixed
2566  *
2567  * Description  close a fixed channel connection. calls no callbacks. idempotent
2568  *
2569  * Returns      void
2570  *
2571  ******************************************************************************/
bta_jv_l2cap_close_fixed(tBTA_JV_MSG * p_data)2572 extern void bta_jv_l2cap_close_fixed(tBTA_JV_MSG* p_data) {
2573   tBTA_JV_API_L2CAP_CLOSE* cc = &(p_data->l2cap_close);
2574   struct fc_client* t;
2575 
2576   t = fcclient_find_by_id(cc->handle);
2577   if (t) fcclient_free(t);
2578 }
2579