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