Home | History | Annotate | Download | only in int
      1 /******************************************************************************
      2  *
      3  *  Copyright (C) 2010-2014 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 LLCP internal definitions
     22  *
     23  ******************************************************************************/
     24 #ifndef LLCP_INT_H
     25 #define LLCP_INT_H
     26 
     27 #include "llcp_api.h"
     28 #include "nfc_api.h"
     29 
     30 /*
     31 ** LLCP link states
     32 */
     33 enum {
     34   LLCP_LINK_STATE_DEACTIVATED,      /* llcp link is deactivated     */
     35   LLCP_LINK_STATE_ACTIVATED,        /* llcp link has been activated */
     36   LLCP_LINK_STATE_DEACTIVATING,     /* llcp link is deactivating    */
     37   LLCP_LINK_STATE_ACTIVATION_FAILED /* llcp link activation was failed */
     38 };
     39 typedef uint8_t tLLCP_LINK_STATE;
     40 
     41 /*
     42 ** LLCP Symmetric state
     43 */
     44 
     45 #define LLCP_LINK_SYMM_LOCAL_XMIT_NEXT 0
     46 #define LLCP_LINK_SYMM_REMOTE_XMIT_NEXT 1
     47 
     48 /*
     49 ** LLCP internal flags
     50 */
     51 /* Received any LLC PDU in activated state */
     52 #define LLCP_LINK_FLAGS_RX_ANY_LLC_PDU 0x01
     53 
     54 /*
     55 ** LLCP link control block
     56 */
     57 typedef struct {
     58   tLLCP_LINK_STATE link_state; /* llcp link state */
     59   tLLCP_LINK_CBACK*
     60       p_link_cback; /* callback function to report llcp link status */
     61   uint16_t wks;     /* well-known service bit-map                   */
     62 
     63   bool is_initiator;    /* TRUE if initiator role                       */
     64   bool is_sending_data; /* TRUE if llcp_link_check_send_data() is excuting    */
     65   uint8_t flags;        /* LLCP internal flags                          */
     66   bool received_first_packet; /* TRUE if a packet has been received from remote
     67                                  */
     68   uint8_t agreed_major_version; /* llcp major version used in activated state */
     69   uint8_t agreed_minor_version; /* llcp minor version used in activated state */
     70 
     71   uint8_t peer_version;   /* llcp version of peer device                  */
     72   uint16_t peer_miu;      /* link MIU of peer device                      */
     73   uint16_t peer_wks;      /* WKS of peer device                           */
     74   uint16_t peer_lto;      /* link timeout of peer device in ms            */
     75   uint8_t peer_opt;       /* Option field of peer device                  */
     76   uint16_t effective_miu; /* MIU to send PDU in activated state           */
     77 
     78   TIMER_LIST_ENT timer; /* link timer for LTO and SYMM response         */
     79   uint8_t symm_state;   /* state of symmectric procedure                */
     80   bool ll_served;       /* TRUE if last transmisstion was for UI        */
     81   uint8_t ll_idx;       /* for scheduler of logical link connection     */
     82   uint8_t dl_idx;       /* for scheduler of data link connection        */
     83 
     84   TIMER_LIST_ENT inact_timer; /* inactivity timer                             */
     85   uint16_t inact_timeout;     /* inactivity timeout in ms                     */
     86 
     87   uint8_t link_deact_reason; /* reason of LLCP link deactivated              */
     88 
     89   BUFFER_Q sig_xmit_q; /* tx signaling PDU queue                       */
     90 
     91   /* runtime configuration parameters */
     92   uint16_t local_link_miu; /* Maximum Information Unit                     */
     93   uint8_t local_opt;       /* Option parameter                             */
     94   uint8_t local_wt;        /* Response Waiting Time Index                  */
     95   uint16_t local_lto;      /* Local Link Timeout                           */
     96   uint16_t inact_timeout_init;   /* Inactivity Timeout as initiator role */
     97   uint16_t inact_timeout_target; /* Inactivity Timeout as target role */
     98   uint16_t symm_delay;        /* Delay SYMM response                          */
     99   uint16_t data_link_timeout; /* data link conneciton timeout                 */
    100   uint16_t delay_first_pdu_timeout; /* delay timeout to send first PDU as
    101                                        initiator */
    102 
    103 } tLLCP_LCB;
    104 
    105 /*
    106 ** LLCP Application's registration control block on service access point (SAP)
    107 */
    108 
    109 typedef struct {
    110   uint8_t link_type;       /* logical link and/or data link                */
    111   uint8_t* p_service_name; /* GKI buffer containing service name           */
    112   tLLCP_APP_CBACK* p_app_cback; /* application's callback pointer */
    113 
    114   BUFFER_Q ui_xmit_q;      /* UI PDU queue for transmitting                */
    115   BUFFER_Q ui_rx_q;        /* UI PDU queue for receiving                   */
    116   bool is_ui_tx_congested; /* TRUE if transmitting UI PDU is congested     */
    117 
    118 } tLLCP_APP_CB;
    119 
    120 /*
    121 ** LLCP data link connection states
    122 */
    123 enum {
    124   LLCP_DLC_STATE_IDLE, /* initial state                                    */
    125   LLCP_DLC_STATE_W4_REMOTE_RESP, /* waiting for connection confirm from peer */
    126   LLCP_DLC_STATE_W4_LOCAL_RESP,  /* waiting for connection confirm from upper
    127                                     layer  */
    128   LLCP_DLC_STATE_CONNECTED,      /* data link connection has been established */
    129   LLCP_DLC_STATE_W4_REMOTE_DM, /* waiting for disconnection confirm from peer */
    130   LLCP_DLC_STATE_MAX
    131 };
    132 typedef uint8_t tLLCP_DLC_STATE;
    133 
    134 /*
    135 ** LLCP data link connection events
    136 */
    137 enum {
    138   LLCP_DLC_EVENT_API_CONNECT_REQ,    /* connection request from upper layer  */
    139   LLCP_DLC_EVENT_API_CONNECT_CFM,    /* connection confirm from upper layer  */
    140   LLCP_DLC_EVENT_API_CONNECT_REJECT, /* connection reject from upper layer   */
    141   LLCP_DLC_EVENT_PEER_CONNECT_IND,   /* connection request from peer         */
    142   LLCP_DLC_EVENT_PEER_CONNECT_CFM,   /* connection confirm from peer         */
    143 
    144   LLCP_DLC_EVENT_API_DATA_REQ,  /* data packet from upper layer         */
    145   LLCP_DLC_EVENT_PEER_DATA_IND, /* data packet from peer                */
    146 
    147   LLCP_DLC_EVENT_API_DISCONNECT_REQ,  /* disconnect request from upper layer  */
    148   LLCP_DLC_EVENT_PEER_DISCONNECT_IND, /* disconnect request from peer         */
    149   LLCP_DLC_EVENT_PEER_DISCONNECT_RESP, /* disconnect response from peer */
    150 
    151   LLCP_DLC_EVENT_FRAME_ERROR, /* received erroneous frame from peer   */
    152   LLCP_DLC_EVENT_LINK_ERROR,  /* llcp link has been deactivated       */
    153 
    154   LLCP_DLC_EVENT_TIMEOUT /* timeout event                        */
    155 };
    156 typedef uint8_t tLLCP_DLC_EVENT;
    157 
    158 /*
    159 ** LLCP data link connection control block
    160 */
    161 
    162 /* send DISC when tx queue is empty       */
    163 #define LLCP_DATA_LINK_FLAG_PENDING_DISC 0x01
    164 /* send RR/RNR with valid sequence        */
    165 #define LLCP_DATA_LINK_FLAG_PENDING_RR_RNR 0x02
    166 /* notify upper later when tx complete    */
    167 #define LLCP_DATA_LINK_FLAG_NOTIFY_TX_DONE 0x04
    168 
    169 typedef struct {
    170   tLLCP_DLC_STATE state;  /* data link connection state               */
    171   uint8_t flags;          /* specific action flags                    */
    172   tLLCP_APP_CB* p_app_cb; /* pointer of application registration      */
    173   TIMER_LIST_ENT timer;   /* timer for connection complete            */
    174 
    175   uint8_t local_sap;  /* SAP of local end point                   */
    176   uint16_t local_miu; /* MIU of local SAP                         */
    177   uint8_t local_rw;   /* RW of local SAP                          */
    178   bool local_busy;    /* TRUE if local SAP is busy                */
    179 
    180   uint8_t remote_sap;  /* SAP of remote end point                  */
    181   uint16_t remote_miu; /* MIU of remote SAP                        */
    182   uint8_t remote_rw;   /* RW of remote SAP                         */
    183   bool remote_busy;    /* TRUE if remote SAP is busy               */
    184 
    185   uint8_t next_tx_seq;  /* V(S), send state variable                */
    186   uint8_t rcvd_ack_seq; /* V(SA), send ack state variable           */
    187   uint8_t next_rx_seq;  /* V(R), receive state variable             */
    188   uint8_t sent_ack_seq; /* V(RA), receive ack state variable        */
    189 
    190   BUFFER_Q i_xmit_q;    /* tx queue of I PDU                        */
    191   bool is_tx_congested; /* TRUE if tx I PDU is congested            */
    192 
    193   BUFFER_Q i_rx_q;              /* rx queue of I PDU                        */
    194   bool is_rx_congested;         /* TRUE if rx I PDU is congested            */
    195   uint8_t num_rx_i_pdu;         /* number of I PDU in rx queue              */
    196   uint8_t rx_congest_threshold; /* dynamic congest threshold for rx I PDU */
    197 
    198 } tLLCP_DLCB;
    199 
    200 /*
    201 ** LLCP service discovery control block
    202 */
    203 
    204 typedef struct {
    205   uint8_t tid;              /* transaction ID                           */
    206   tLLCP_SDP_CBACK* p_cback; /* callback function for service discovery  */
    207 } tLLCP_SDP_TRANSAC;
    208 
    209 typedef struct {
    210   uint8_t next_tid;                                /* next TID to use         */
    211   tLLCP_SDP_TRANSAC transac[LLCP_MAX_SDP_TRANSAC]; /* active SDP transactions */
    212   NFC_HDR* p_snl;                                  /* buffer for SNL PDU      */
    213 } tLLCP_SDP_CB;
    214 
    215 /*
    216 ** LLCP control block
    217 */
    218 
    219 typedef struct {
    220   uint8_t trace_level; /* LLCP trace level                             */
    221 
    222   tLLCP_SDP_CB sdp_cb; /* SDP control block                            */
    223   tLLCP_LCB lcb;       /* LLCP link control block                      */
    224   tLLCP_APP_CB wks_cb[LLCP_MAX_WKS]; /* Application's registration for
    225                                         well-known services */
    226   tLLCP_APP_CB server_cb
    227       [LLCP_MAX_SERVER]; /* Application's registration for SDP services  */
    228   tLLCP_APP_CB
    229       client_cb[LLCP_MAX_CLIENT]; /* Application's registration for client */
    230   tLLCP_DLCB dlcb[LLCP_MAX_DATA_LINK]; /* Data link connection control block */
    231 
    232   uint8_t max_num_ll_tx_buff; /* max number of tx UI PDU in queue             */
    233   uint8_t max_num_tx_buff;    /* max number of tx UI/I PDU in queue           */
    234 
    235   uint8_t num_logical_data_link; /* number of logical data link */
    236   uint8_t
    237       num_data_link_connection; /* number of established data link connection */
    238 
    239   /* these two thresholds (number of tx UI PDU) are dynamically adjusted based
    240    * on number of logical links */
    241   uint8_t
    242       ll_tx_congest_start;   /* congest start threshold for each logical link*/
    243   uint8_t ll_tx_congest_end; /* congest end threshold for each logical link  */
    244 
    245   uint8_t total_tx_ui_pdu;   /* total number of tx UI PDU in all of ui_xmit_q*/
    246   uint8_t total_tx_i_pdu;    /* total number of tx I PDU in all of i_xmit_q  */
    247   bool overall_tx_congested; /* TRUE if tx link is congested                 */
    248 
    249   /* start point of uncongested status notification is in round robin */
    250   uint8_t ll_tx_uncongest_ntf_start_sap; /* next start of logical data link */
    251   uint8_t
    252       dl_tx_uncongest_ntf_start_idx; /* next start of data link connection */
    253 
    254   /*
    255   ** when overall rx link congestion starts, RNR is sent to remote end point
    256   ** of data link connection while rx link is congested, UI PDU is discarded.
    257   */
    258   uint8_t num_rx_buff; /* reserved number of rx UI/I PDU in queue      */
    259   uint8_t
    260       overall_rx_congest_start;   /* threshold of overall rx congestion start */
    261   uint8_t overall_rx_congest_end; /* threshold of overall rx congestion end */
    262   uint8_t max_num_ll_rx_buff; /* max number of rx UI PDU in queue             */
    263 
    264   /*
    265   ** threshold (number of rx UI PDU) is dynamically adjusted based on number
    266   ** of logical links when number of rx UI PDU is more than
    267   ** ll_rx_congest_start, the oldest UI PDU is discarded
    268   */
    269   uint8_t ll_rx_congest_start; /* rx congest start threshold for each logical
    270                                   link */
    271 
    272   uint8_t total_rx_ui_pdu;   /* total number of rx UI PDU in all of ui_rx_q  */
    273   uint8_t total_rx_i_pdu;    /* total number of rx I PDU in all of i_rx_q    */
    274   bool overall_rx_congested; /* TRUE if overall rx link is congested         */
    275 } tLLCP_CB;
    276 
    277 #if (LLCP_TEST_INCLUDED == TRUE) /* this is for LLCP testing */
    278 
    279 typedef struct {
    280   uint8_t version;
    281   uint16_t wks;
    282 } tLLCP_TEST_PARAMS;
    283 
    284 #endif
    285 
    286 #ifdef __cplusplus
    287 extern "C" {
    288 #endif
    289 
    290 /*
    291 ** LLCP global data
    292 */
    293 
    294 extern tLLCP_CB llcp_cb;
    295 
    296 /*
    297 ** Functions provided by llcp_main.c
    298 */
    299 void llcp_init(void);
    300 void llcp_cleanup(void);
    301 void llcp_process_timeout(TIMER_LIST_ENT* p_tle);
    302 
    303 /*
    304 ** Functions provided by llcp_link.c
    305 */
    306 tLLCP_STATUS llcp_link_activate(tLLCP_ACTIVATE_CONFIG* p_config);
    307 void llcp_link_process_link_timeout(void);
    308 void llcp_link_deactivate(uint8_t reason);
    309 
    310 void llcp_link_check_send_data(void);
    311 void llcp_link_connection_cback(uint8_t conn_id, tNFC_CONN_EVT event,
    312                                 tNFC_CONN* p_data);
    313 
    314 /*
    315 **  Functions provided by llcp_util.c
    316 */
    317 void llcp_util_adjust_ll_congestion(void);
    318 void llcp_util_adjust_dl_rx_congestion(void);
    319 void llcp_util_check_rx_congested_status(void);
    320 bool llcp_util_parse_link_params(uint16_t length, uint8_t* p_bytes);
    321 tLLCP_STATUS llcp_util_send_ui(uint8_t ssap, uint8_t dsap,
    322                                tLLCP_APP_CB* p_app_cb, NFC_HDR* p_msg);
    323 void llcp_util_send_disc(uint8_t dsap, uint8_t ssap);
    324 tLLCP_DLCB* llcp_util_allocate_data_link(uint8_t reg_sap, uint8_t remote_sap);
    325 void llcp_util_deallocate_data_link(tLLCP_DLCB* p_dlcb);
    326 tLLCP_STATUS llcp_util_send_connect(tLLCP_DLCB* p_dlcb,
    327                                     tLLCP_CONNECTION_PARAMS* p_params);
    328 tLLCP_STATUS llcp_util_parse_connect(uint8_t* p_bytes, uint16_t length,
    329                                      tLLCP_CONNECTION_PARAMS* p_params);
    330 tLLCP_STATUS llcp_util_send_cc(tLLCP_DLCB* p_dlcb,
    331                                tLLCP_CONNECTION_PARAMS* p_params);
    332 tLLCP_STATUS llcp_util_parse_cc(uint8_t* p_bytes, uint16_t length,
    333                                 uint16_t* p_miu, uint8_t* p_rw);
    334 void llcp_util_send_dm(uint8_t dsap, uint8_t ssap, uint8_t reason);
    335 void llcp_util_build_info_pdu(tLLCP_DLCB* p_dlcb, NFC_HDR* p_msg);
    336 tLLCP_STATUS llcp_util_send_frmr(tLLCP_DLCB* p_dlcb, uint8_t flags,
    337                                  uint8_t ptype, uint8_t sequence);
    338 void llcp_util_send_rr_rnr(tLLCP_DLCB* p_dlcb);
    339 tLLCP_APP_CB* llcp_util_get_app_cb(uint8_t sap);
    340 /*
    341 ** Functions provided by llcp_dlc.c
    342 */
    343 tLLCP_STATUS llcp_dlsm_execute(tLLCP_DLCB* p_dlcb, tLLCP_DLC_EVENT event,
    344                                void* p_data);
    345 tLLCP_DLCB* llcp_dlc_find_dlcb_by_sap(uint8_t local_sap, uint8_t remote_sap);
    346 void llcp_dlc_flush_q(tLLCP_DLCB* p_dlcb);
    347 void llcp_dlc_proc_i_pdu(uint8_t dsap, uint8_t ssap, uint16_t i_pdu_length,
    348                          uint8_t* p_i_pdu, NFC_HDR* p_msg);
    349 void llcp_dlc_proc_rx_pdu(uint8_t dsap, uint8_t ptype, uint8_t ssap,
    350                           uint16_t length, uint8_t* p_data);
    351 void llcp_dlc_check_to_send_rr_rnr(void);
    352 bool llcp_dlc_is_rw_open(tLLCP_DLCB* p_dlcb);
    353 NFC_HDR* llcp_dlc_get_next_pdu(tLLCP_DLCB* p_dlcb);
    354 uint16_t llcp_dlc_get_next_pdu_length(tLLCP_DLCB* p_dlcb);
    355 
    356 /*
    357 ** Functions provided by llcp_sdp.c
    358 */
    359 void llcp_sdp_proc_data(tLLCP_SAP_CBACK_DATA* p_data);
    360 tLLCP_STATUS llcp_sdp_send_sdreq(uint8_t tid, char* p_name);
    361 uint8_t llcp_sdp_get_sap_by_name(char* p_name, uint8_t length);
    362 tLLCP_STATUS llcp_sdp_proc_snl(uint16_t sdu_length, uint8_t* p);
    363 void llcp_sdp_check_send_snl(void);
    364 void llcp_sdp_proc_deactivation(void);
    365 #ifdef __cplusplus
    366 }
    367 #endif
    368 
    369 #endif
    370