Home | History | Annotate | Download | only in pan
      1 /******************************************************************************
      2  *
      3  *  Copyright (C) 1999-2012 Broadcom Corporation
      4  *
      5  *  Licensed under the Apache License, Version 2.0 (the "License");
      6  *  you may not use this file except in compliance with the License.
      7  *  You may obtain a copy of the License at:
      8  *
      9  *  http://www.apache.org/licenses/LICENSE-2.0
     10  *
     11  *  Unless required by applicable law or agreed to in writing, software
     12  *  distributed under the License is distributed on an "AS IS" BASIS,
     13  *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     14  *  See the License for the specific language governing permissions and
     15  *  limitations under the License.
     16  *
     17  ******************************************************************************/
     18 
     19 /*****************************************************************************
     20  *
     21  *  This file contains main functions to support PAN profile
     22  *  commands and events.
     23  *
     24  *****************************************************************************/
     25 
     26 #include <string.h>
     27 #include <stdio.h>
     28 #include "gki.h"
     29 #include "bnep_api.h"
     30 #include "pan_api.h"
     31 #include "pan_int.h"
     32 #include "sdp_api.h"
     33 #include "sdpdefs.h"
     34 #include "l2c_api.h"
     35 #include "hcidefs.h"
     36 #include "btm_api.h"
     37 
     38 
     39 static const UINT8 pan_proto_elem_data[]   = {
     40                                    0x35, 0x18,          /* data element sequence of length 0x18 bytes */
     41                                    0x35, 0x06,          /* data element sequence for L2CAP descriptor */
     42                                    0x19, 0x01, 0x00,    /* UUID for L2CAP - 0x0100 */
     43                                    0x09, 0x00, 0x0F,    /* PSM for BNEP - 0x000F */
     44                                    0x35, 0x0E,          /* data element seqence for BNEP descriptor */
     45                                    0x19, 0x00, 0x0F,    /* UUID for BNEP - 0x000F */
     46                                    0x09, 0x01, 0x00,    /* BNEP specific parameter 0 -- Version of BNEP = version 1 = 0x0001 */
     47                                    0x35, 0x06,          /* BNEP specific parameter 1 -- Supported network packet type list */
     48                                    0x09, 0x08, 0x00,    /* network packet type IPv4 = 0x0800 */
     49                                    0x09, 0x08, 0x06     /* network packet type ARP  = 0x0806 */
     50 };
     51 
     52 /*******************************************************************************
     53 **
     54 ** Function         pan_register_with_sdp
     55 **
     56 ** Description
     57 **
     58 ** Returns
     59 **
     60 *******************************************************************************/
     61 UINT32 pan_register_with_sdp (UINT16 uuid, UINT8 sec_mask, char *p_name, char *p_desc)
     62 {
     63     UINT32  sdp_handle;
     64     UINT16  browse_list = UUID_SERVCLASS_PUBLIC_BROWSE_GROUP;
     65     UINT16  security = 0;
     66     UINT32  proto_len = (UINT32)pan_proto_elem_data[1];
     67 
     68     /* Create a record */
     69     sdp_handle = SDP_CreateRecord ();
     70 
     71     if (sdp_handle == 0)
     72     {
     73         PAN_TRACE_ERROR ("PAN_SetRole - could not create SDP record");
     74         return 0;
     75     }
     76 
     77     /* Service Class ID List */
     78     SDP_AddServiceClassIdList (sdp_handle, 1, &uuid);
     79 
     80     /* Add protocol element sequence from the constant string */
     81     SDP_AddAttribute (sdp_handle, ATTR_ID_PROTOCOL_DESC_LIST, DATA_ELE_SEQ_DESC_TYPE,
     82                       proto_len, (UINT8 *)(pan_proto_elem_data+2));
     83 
     84 // btla-specific ++
     85 #if 0
     86     availability = 0xFF;
     87     SDP_AddAttribute (sdp_handle, ATTR_ID_SERVICE_AVAILABILITY, UINT_DESC_TYPE, 1, &availability);
     88 #endif
     89 // btla-specific --
     90 
     91     /* Language base */
     92     SDP_AddLanguageBaseAttrIDList (sdp_handle, LANG_ID_CODE_ENGLISH, LANG_ID_CHAR_ENCODE_UTF8, LANGUAGE_BASE_ID);
     93 
     94     /* Profile descriptor list */
     95     SDP_AddProfileDescriptorList (sdp_handle, uuid, PAN_PROFILE_VERSION);
     96 
     97     /* Service Name */
     98     SDP_AddAttribute (sdp_handle, ATTR_ID_SERVICE_NAME, TEXT_STR_DESC_TYPE,
     99                         (UINT8) (strlen(p_name) + 1), (UINT8 *)p_name);
    100 
    101     /* Service description */
    102     SDP_AddAttribute (sdp_handle, ATTR_ID_SERVICE_DESCRIPTION, TEXT_STR_DESC_TYPE,
    103                         (UINT8) (strlen(p_desc) + 1), (UINT8 *)p_desc);
    104 
    105     /* Security description */
    106     if (sec_mask)
    107     {
    108         UINT16_TO_BE_FIELD(&security, 0x0001);
    109     }
    110     SDP_AddAttribute (sdp_handle, ATTR_ID_SECURITY_DESCRIPTION, UINT_DESC_TYPE, 2, (UINT8 *)&security);
    111 
    112 #if (defined (PAN_SUPPORTS_ROLE_NAP) && PAN_SUPPORTS_ROLE_NAP == TRUE)
    113     if (uuid == UUID_SERVCLASS_NAP)
    114     {
    115         UINT16  NetAccessType = 0x0005;      /* Ethernet */
    116         UINT32  NetAccessRate = 0x0001312D0; /* 10Mb/sec */
    117         UINT8   array[10], *p;
    118 
    119         /* Net access type. */
    120         p = array;
    121         UINT16_TO_BE_STREAM (p, NetAccessType);
    122         SDP_AddAttribute (sdp_handle, ATTR_ID_NET_ACCESS_TYPE, UINT_DESC_TYPE, 2, array);
    123 
    124         /* Net access rate. */
    125         p = array;
    126         UINT32_TO_BE_STREAM (p, NetAccessRate);
    127         SDP_AddAttribute (sdp_handle, ATTR_ID_MAX_NET_ACCESS_RATE, UINT_DESC_TYPE, 4, array);
    128 
    129         /* Register with Security Manager for the specific security level */
    130         if ((!BTM_SetSecurityLevel (TRUE, p_name, BTM_SEC_SERVICE_BNEP_NAP,
    131                                     sec_mask, BT_PSM_BNEP, BTM_SEC_PROTO_BNEP, UUID_SERVCLASS_NAP))
    132          || (!BTM_SetSecurityLevel (FALSE, p_name, BTM_SEC_SERVICE_BNEP_NAP,
    133                                     sec_mask, BT_PSM_BNEP, BTM_SEC_PROTO_BNEP, UUID_SERVCLASS_NAP)))
    134         {
    135             PAN_TRACE_ERROR ("PAN Security Registration failed for PANU");
    136         }
    137     }
    138 #endif
    139 #if (defined (PAN_SUPPORTS_ROLE_GN) && PAN_SUPPORTS_ROLE_GN == TRUE)
    140     if (uuid == UUID_SERVCLASS_GN)
    141     {
    142         if ((!BTM_SetSecurityLevel (TRUE, p_name, BTM_SEC_SERVICE_BNEP_GN,
    143                                     sec_mask, BT_PSM_BNEP, BTM_SEC_PROTO_BNEP, UUID_SERVCLASS_GN))
    144          || (!BTM_SetSecurityLevel (FALSE, p_name, BTM_SEC_SERVICE_BNEP_GN,
    145                                     sec_mask, BT_PSM_BNEP, BTM_SEC_PROTO_BNEP, UUID_SERVCLASS_GN)))
    146         {
    147             PAN_TRACE_ERROR ("PAN Security Registration failed for GN");
    148         }
    149     }
    150 #endif
    151 #if (defined (PAN_SUPPORTS_ROLE_PANU) && PAN_SUPPORTS_ROLE_PANU == TRUE)
    152     if (uuid == UUID_SERVCLASS_PANU)
    153     {
    154         if ((!BTM_SetSecurityLevel (TRUE, p_name, BTM_SEC_SERVICE_BNEP_PANU,
    155                                     sec_mask, BT_PSM_BNEP, BTM_SEC_PROTO_BNEP, UUID_SERVCLASS_PANU))
    156          || (!BTM_SetSecurityLevel (FALSE, p_name, BTM_SEC_SERVICE_BNEP_PANU,
    157                                     sec_mask, BT_PSM_BNEP, BTM_SEC_PROTO_BNEP, UUID_SERVCLASS_PANU)))
    158         {
    159             PAN_TRACE_ERROR ("PAN Security Registration failed for PANU");
    160         }
    161     }
    162 #endif
    163 
    164     /* Make the service browsable */
    165     SDP_AddUuidSequence (sdp_handle,  ATTR_ID_BROWSE_GROUP_LIST, 1, &browse_list);
    166 
    167 
    168     return sdp_handle;
    169 }
    170 
    171 
    172 
    173 /*******************************************************************************
    174 **
    175 ** Function         pan_allocate_pcb
    176 **
    177 ** Description
    178 **
    179 ** Returns
    180 **
    181 *******************************************************************************/
    182 tPAN_CONN *pan_allocate_pcb (BD_ADDR p_bda, UINT16 handle)
    183 {
    184     UINT16      i;
    185 
    186     for (i=0; i<MAX_PAN_CONNS; i++)
    187     {
    188         if (pan_cb.pcb[i].con_state != PAN_STATE_IDLE &&
    189             pan_cb.pcb[i].handle == handle)
    190             return NULL;
    191     }
    192 
    193     for (i=0; i<MAX_PAN_CONNS; i++)
    194     {
    195         if (pan_cb.pcb[i].con_state != PAN_STATE_IDLE &&
    196             memcmp (pan_cb.pcb[i].rem_bda, p_bda, BD_ADDR_LEN) == 0)
    197             return NULL;
    198     }
    199 
    200     for (i=0; i<MAX_PAN_CONNS; i++)
    201     {
    202         if (pan_cb.pcb[i].con_state == PAN_STATE_IDLE)
    203         {
    204             memset (&(pan_cb.pcb[i]), 0, sizeof (tPAN_CONN));
    205             memcpy (pan_cb.pcb[i].rem_bda, p_bda, BD_ADDR_LEN);
    206             pan_cb.pcb[i].handle = handle;
    207             return &(pan_cb.pcb[i]);
    208         }
    209     }
    210     return NULL;
    211 }
    212 
    213 
    214 /*******************************************************************************
    215 **
    216 ** Function         pan_get_pcb_by_handle
    217 **
    218 ** Description
    219 **
    220 ** Returns
    221 **
    222 *******************************************************************************/
    223 tPAN_CONN *pan_get_pcb_by_handle (UINT16 handle)
    224 {
    225     UINT16      i;
    226 
    227     for (i=0; i<MAX_PAN_CONNS; i++)
    228     {
    229         if (pan_cb.pcb[i].con_state != PAN_STATE_IDLE &&
    230             pan_cb.pcb[i].handle == handle)
    231             return &(pan_cb.pcb[i]);
    232     }
    233 
    234     return NULL;
    235 }
    236 
    237 
    238 /*******************************************************************************
    239 **
    240 ** Function         pan_get_pcb_by_addr
    241 **
    242 ** Description
    243 **
    244 ** Returns
    245 **
    246 *******************************************************************************/
    247 tPAN_CONN *pan_get_pcb_by_addr (BD_ADDR p_bda)
    248 {
    249     UINT16      i;
    250 
    251     for (i=0; i<MAX_PAN_CONNS; i++)
    252     {
    253         if (pan_cb.pcb[i].con_state == PAN_STATE_IDLE)
    254             continue;
    255 
    256         if (memcmp (pan_cb.pcb[i].rem_bda, p_bda, BD_ADDR_LEN) == 0)
    257             return &(pan_cb.pcb[i]);
    258 
    259         /*
    260         if (pan_cb.pcb[i].mfilter_present &&
    261             (memcmp (p_bda, pan_cb.pcb[i].multi_cast_bridge, BD_ADDR_LEN) == 0))
    262             return &(pan_cb.pcb[i]);
    263         */
    264     }
    265 
    266     return NULL;
    267 }
    268 
    269 
    270 
    271 
    272 /*******************************************************************************
    273 **
    274 ** Function         pan_close_all_connections
    275 **
    276 ** Description
    277 **
    278 ** Returns          void
    279 **
    280 *******************************************************************************/
    281 void pan_close_all_connections (void)
    282 {
    283     UINT16      i;
    284 
    285     for (i=0; i<MAX_PAN_CONNS; i++)
    286     {
    287         if (pan_cb.pcb[i].con_state != PAN_STATE_IDLE)
    288         {
    289             BNEP_Disconnect (pan_cb.pcb[i].handle);
    290             pan_cb.pcb[i].con_state = PAN_STATE_IDLE;
    291         }
    292     }
    293 
    294     pan_cb.active_role = PAN_ROLE_INACTIVE;
    295     pan_cb.num_conns   = 0;
    296     return;
    297 }
    298 
    299 
    300 /*******************************************************************************
    301 **
    302 ** Function         pan_release_pcb
    303 **
    304 ** Description      This function releases a PCB.
    305 **
    306 ** Returns          void
    307 **
    308 *******************************************************************************/
    309 void pan_release_pcb (tPAN_CONN *p_pcb)
    310 {
    311     /* Drop any response pointer we may be holding */
    312     memset (p_pcb, 0, sizeof (tPAN_CONN));
    313     p_pcb->con_state = PAN_STATE_IDLE;
    314 }
    315 
    316 
    317 /*******************************************************************************
    318 **
    319 ** Function         pan_dump_status
    320 **
    321 ** Description      This function dumps the pan control block and connection
    322 **                  blocks information
    323 **
    324 ** Returns          none
    325 **
    326 *******************************************************************************/
    327 void pan_dump_status (void)
    328 {
    329 #if (defined (PAN_SUPPORTS_DEBUG_DUMP) && PAN_SUPPORTS_DEBUG_DUMP == TRUE)
    330     UINT16          i;
    331     char            buff[200];
    332     tPAN_CONN      *p_pcb;
    333 
    334     PAN_TRACE_DEBUG ("PAN role %x, active role %d, num_conns %d",
    335         pan_cb.role, pan_cb.active_role, pan_cb.num_conns);
    336 
    337     for (i = 0, p_pcb = pan_cb.pcb; i < MAX_PAN_CONNS; i++, p_pcb++)
    338     {
    339         sprintf (buff, "%d state %d, handle %d, src 0x%x, dst 0x%x, BD %x.%x.%x.%x.%x.%x",
    340             i, p_pcb->con_state, p_pcb->handle, p_pcb->src_uuid, p_pcb->dst_uuid,
    341             p_pcb->rem_bda[0], p_pcb->rem_bda[1], p_pcb->rem_bda[2],
    342             p_pcb->rem_bda[3], p_pcb->rem_bda[4], p_pcb->rem_bda[5]);
    343 
    344         PAN_TRACE_DEBUG (buff);
    345     }
    346 #endif
    347 }
    348 
    349 
    350 
    351