Ejemplo n.º 1
0
/*******************************************************************************
**
** Function         avdt_ad_tc_data_ind
**
** Description      This function is called by the L2CAP interface layer when
**                  incoming data is received from L2CAP.  It looks up the CCB
**                  or SCB for the channel and routes the data accordingly.
**
**
** Returns          Nothing.
**
*******************************************************************************/
void avdt_ad_tc_data_ind(tAVDT_TC_TBL *p_tbl, BT_HDR *p_buf)
{
    tAVDT_CCB   *p_ccb;
    tAVDT_SCB   *p_scb;

    /* store type (media, recovery, reporting) */
    p_buf->layer_specific = avdt_ad_tcid_to_type(p_tbl->tcid);


    /* if signaling channel, handle control message */
    if (p_tbl->tcid == 0) {
        p_ccb = avdt_ccb_by_idx(p_tbl->ccb_idx);
        avdt_msg_ind(p_ccb, p_buf);
    }
    /* if media or other channel, send event to scb */
    else {
        p_scb = avdt_scb_by_hdl(avdt_cb.ad.rt_tbl[p_tbl->ccb_idx][p_tbl->tcid].scb_hdl);
        if (p_scb != NULL) {
            avdt_scb_event(p_scb, AVDT_SCB_TC_DATA_EVT, (tAVDT_SCB_EVT *) &p_buf);
        } else {
            GKI_freebuf(p_buf);
            AVDT_TRACE_ERROR(" avdt_ad_tc_data_ind buffer freed");
        }
    }
}
Ejemplo n.º 2
0
/*******************************************************************************
**
** Function         avdt_ad_tc_close_ind
**
** Description      This function is called by the L2CAP interface when the
**                  L2CAP channel is closed.  It looks up the CCB or SCB for
**                  the channel and sends it a close event.  The reason
**                  parameter is the same value passed by the L2CAP
**                  callback function.
**
**
** Returns          Nothing.
**
*******************************************************************************/
void avdt_ad_tc_close_ind(tAVDT_TC_TBL *p_tbl, UINT16 reason)
{
    tAVDT_CCB   *p_ccb;
    tAVDT_SCB   *p_scb;
    tAVDT_SCB_TC_CLOSE  close;
    // UNUSED(reason);

    close.old_tc_state = p_tbl->state;

    /* clear avdt_ad_tc_tbl entry */
    p_tbl->state = AVDT_AD_ST_UNUSED;
    p_tbl->cfg_flags = 0;
    p_tbl->peer_mtu = L2CAP_DEFAULT_MTU;

    AVDT_TRACE_DEBUG("avdt_ad_tc_close_ind tcid: %d, old: %d\n",
                     p_tbl->tcid, close.old_tc_state);

    /* if signaling channel, notify ccb that channel open */
    if (p_tbl->tcid == 0) {
        p_ccb = avdt_ccb_by_idx(p_tbl->ccb_idx);
        p_ccb->disc_rsn = (reason == AVDT_DISC_RSN_ABNORMAL) ? AVDT_DISC_RSN_ABNORMAL : AVDT_DISC_RSN_NORMAL;
        avdt_ccb_event(p_ccb, AVDT_CCB_LL_CLOSE_EVT, NULL);
    }
    /* if media or other channel, notify scb that channel close */
    else {
        /* look up scb in stream routing table by ccb, tcid */
        p_scb = avdt_scb_by_hdl(avdt_cb.ad.rt_tbl[p_tbl->ccb_idx][p_tbl->tcid].scb_hdl);
        if (p_scb != NULL) {
            close.tcid = p_tbl->tcid;
            close.type = avdt_ad_tcid_to_type(p_tbl->tcid);
            close.disc_rsn = (reason == AVDT_DISC_RSN_ABNORMAL) ? AVDT_DISC_RSN_ABNORMAL : AVDT_DISC_RSN_NORMAL;
            avdt_scb_event(p_scb, AVDT_SCB_TC_CLOSE_EVT, (tAVDT_SCB_EVT *)&close);
        }
    }
}
Ejemplo n.º 3
0
/*******************************************************************************
**
** Function         avdt_l2c_connect_cfm_cback
**
** Description      This is the L2CAP connect confirm callback function.
**
**
** Returns          void
**
*******************************************************************************/
void avdt_l2c_connect_cfm_cback(UINT16 lcid, UINT16 result)
{
    tAVDT_TC_TBL    *p_tbl;
    tL2CAP_CFG_INFO cfg;
    tAVDT_CCB *p_ccb;

    AVDT_TRACE_DEBUG("avdt_l2c_connect_cfm_cback lcid: %d, result: %d\n",
                     lcid, result);
    /* look up info for this channel */
    if ((p_tbl = avdt_ad_tc_tbl_by_lcid(lcid)) != NULL) {
        /* if in correct state */
        if (p_tbl->state == AVDT_AD_ST_CONN) {
            /* if result successful */
            if (result == L2CAP_CONN_OK) {
                if (p_tbl->tcid != AVDT_CHAN_SIG) {
                    /* set channel state */
                    p_tbl->state = AVDT_AD_ST_CFG;

                    /* Send L2CAP config req */
                    memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
                    cfg.mtu_present = TRUE;
                    cfg.mtu = p_tbl->my_mtu;
                    cfg.flush_to_present = TRUE;
                    cfg.flush_to = p_tbl->my_flush_to;
                    L2CA_ConfigReq(lcid, &cfg);
                } else {
                    p_ccb = avdt_ccb_by_idx(p_tbl->ccb_idx);
                    if (p_ccb == NULL) {
                        result = L2CAP_CONN_NO_RESOURCES;
                    } else {
                        /* set channel state */
                        p_tbl->state = AVDT_AD_ST_SEC_INT;
                        p_tbl->lcid = lcid;
                        p_tbl->cfg_flags = AVDT_L2C_CFG_CONN_INT;

                        /* Check the security */
                        btm_sec_mx_access_request (p_ccb->peer_addr, AVDT_PSM,
                                                   TRUE, BTM_SEC_PROTO_AVDT,
                                                   AVDT_CHAN_SIG,
                                                   &avdt_sec_check_complete_orig, NULL);
                    }
                }
            }

            /* failure; notify adaption that channel closed */
            if (result != L2CAP_CONN_OK) {
                avdt_ad_tc_close_ind(p_tbl, result);
            }
        }
    }
}
Ejemplo n.º 4
0
/*******************************************************************************
**
** Function         avdt_ad_tc_cong_ind
**
** Description      This function is called by the L2CAP interface layer when
**                  L2CAP calls the congestion callback.  It looks up the CCB
**                  or SCB for the channel and sends it a congestion event.
**                  The is_congested parameter is the same value passed by
**                  the L2CAP callback function.
**
**
** Returns          Nothing.
**
*******************************************************************************/
void avdt_ad_tc_cong_ind(tAVDT_TC_TBL *p_tbl, BOOLEAN is_congested)
{
    tAVDT_CCB   *p_ccb;
    tAVDT_SCB   *p_scb;

    /* if signaling channel, notify ccb of congestion */
    if (p_tbl->tcid == 0) {
        p_ccb = avdt_ccb_by_idx(p_tbl->ccb_idx);
        avdt_ccb_event(p_ccb, AVDT_CCB_LL_CONG_EVT, (tAVDT_CCB_EVT *) &is_congested);
    }
    /* if media or other channel, notify scb that channel open */
    else {
        /* look up scb in stream routing table by ccb, tcid */
        p_scb = avdt_scb_by_hdl(avdt_cb.ad.rt_tbl[p_tbl->ccb_idx][p_tbl->tcid].scb_hdl);
        if (p_scb != NULL) {
            avdt_scb_event(p_scb, AVDT_SCB_TC_CONG_EVT, (tAVDT_SCB_EVT *) &is_congested);
        }
    }
}
Ejemplo n.º 5
0
/*******************************************************************************
**
** Function         avdt_ad_tc_open_ind
**
** Description      This function is called by the L2CAP interface when
**                  the L2CAP channel is opened.  It looks up the CCB or SCB
**                  for the channel and sends it an open event.
**
**
** Returns          Nothing.
**
*******************************************************************************/
void avdt_ad_tc_open_ind(tAVDT_TC_TBL *p_tbl)
{
    tAVDT_CCB   *p_ccb;
    tAVDT_SCB   *p_scb;
    tAVDT_OPEN  open;
    tAVDT_EVT_HDR evt;

    p_tbl->state = AVDT_AD_ST_OPEN;

    /* if signaling channel, notify ccb that channel open */
    if (p_tbl->tcid == 0) {
        /* set the signal channel to use high priority within the ACL link */
        L2CA_SetTxPriority(avdt_cb.ad.rt_tbl[p_tbl->ccb_idx][AVDT_CHAN_SIG].lcid, L2CAP_CHNL_PRIORITY_HIGH);

        p_ccb = avdt_ccb_by_idx(p_tbl->ccb_idx);
        /* use err_param to indicate the role of connection.
         * AVDT_ACP, if ACP */
        evt.err_param = AVDT_INT;
        if (p_tbl->cfg_flags & AVDT_L2C_CFG_CONN_ACP) {
            evt.err_param = AVDT_ACP;
        }
        avdt_ccb_event(p_ccb, AVDT_CCB_LL_OPEN_EVT, (tAVDT_CCB_EVT *)&evt);
    }
    /* if media or other channel, notify scb that channel open */
    else {
        /* look up scb in stream routing table by ccb, tcid */
        p_scb = avdt_scb_by_hdl(avdt_cb.ad.rt_tbl[p_tbl->ccb_idx][p_tbl->tcid].scb_hdl);

        /* put lcid in event data */
        if (p_scb != NULL) {
            open.peer_mtu = p_tbl->peer_mtu;
            open.lcid = avdt_cb.ad.rt_tbl[p_tbl->ccb_idx][p_tbl->tcid].lcid;
            open.hdr.err_code = avdt_ad_tcid_to_type(p_tbl->tcid);
            avdt_scb_event(p_scb, AVDT_SCB_TC_OPEN_EVT, (tAVDT_SCB_EVT *) &open);
        }
    }
}