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