avrc_api.c revision 9adddf4965e9ddb01e339b934c343fcbd842a977
15738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
25738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
35738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  Copyright (C) 2003-2012 Broadcom Corporation
45738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
55738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  Licensed under the Apache License, Version 2.0 (the "License");
65738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  you may not use this file except in compliance with the License.
75738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  You may obtain a copy of the License at:
85738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
95738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  http://www.apache.org/licenses/LICENSE-2.0
105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  Unless required by applicable law or agreed to in writing, software
125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  distributed under the License is distributed on an "AS IS" BASIS,
135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  See the License for the specific language governing permissions and
155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  limitations under the License.
165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project ******************************************************************************/
185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
219adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan *  Interface to AVRCP mandatory commands
225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project ******************************************************************************/
245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include <string.h>
255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "gki.h"
275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "avrc_api.h"
285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "avrc_int.h"
295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "wcassert.h"
305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*****************************************************************************
325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**  Global data
335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*****************************************************************************/
345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#define AVRC_MAX_RCV_CTRL_EVT   AVCT_BROWSE_UNCONG_IND_EVT
375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic const UINT8 avrc_ctrl_event_map[] =
395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    AVRC_OPEN_IND_EVT,  /* AVCT_CONNECT_CFM_EVT */
415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    AVRC_OPEN_IND_EVT,  /* AVCT_CONNECT_IND_EVT */
425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    AVRC_CLOSE_IND_EVT, /* AVCT_DISCONNECT_CFM_EVT */
435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    AVRC_CLOSE_IND_EVT, /* AVCT_DISCONNECT_IND_EVT */
445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    AVRC_CONG_IND_EVT,  /* AVCT_CONG_IND_EVT */
455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    AVRC_UNCONG_IND_EVT,/* AVCT_UNCONG_IND_EVT */
465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    AVRC_BROWSE_OPEN_IND_EVT,  /* AVCT_BROWSE_CONN_CFM_EVT   */
475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    AVRC_BROWSE_OPEN_IND_EVT,  /* AVCT_BROWSE_CONN_IND_EVT   */
485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    AVRC_BROWSE_CLOSE_IND_EVT, /* AVCT_BROWSE_DISCONN_CFM_EVT */
495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    AVRC_BROWSE_CLOSE_IND_EVT, /* AVCT_BROWSE_DISCONN_IND_EVT */
505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    AVRC_BROWSE_CONG_IND_EVT,  /* AVCT_BROWSE_CONG_IND_EVT    */
515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    AVRC_BROWSE_UNCONG_IND_EVT /* AVCT_BROWSE_UNCONG_IND_EVT  */
525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project};
535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#define AVRC_OP_DROP        0xFE    /* use this unused opcode to indication no need to call the callback function */
555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#define AVRC_OP_DROP_N_FREE 0xFD    /* use this unused opcode to indication no need to call the callback function & free buffer */
565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         avrc_ctrl_cback
605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This is the callback function used by AVCTP to report
625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  received link events.
635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          Nothing.
655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project******************************************************************************/
675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void avrc_ctrl_cback(UINT8 handle, UINT8 event, UINT16 result,
685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                                BD_ADDR peer_addr)
695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8   avrc_event;
715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (event <= AVRC_MAX_RCV_CTRL_EVT && avrc_cb.ccb[handle].p_ctrl_cback)
735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        avrc_event = avrc_ctrl_event_map[event];
755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if (event == AVCT_CONNECT_CFM_EVT)
765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            if (result != 0) /* failed */
785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                avrc_event = AVRC_CLOSE_IND_EVT;
795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        (*avrc_cb.ccb[handle].p_ctrl_cback)(handle, avrc_event, result, peer_addr);
815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* else drop the unknown event*/
835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         avrc_get_data_ptr
885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      If the offset in the received buffer is smaller than required
905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  move the portion of data AVRC cares.
915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          Nothing.
935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project******************************************************************************/
955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic UINT8 * avrc_get_data_ptr(BT_HDR *p_pkt)
965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8   *p_data = (UINT8 *)(p_pkt+1) + p_pkt->offset;
985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    int     i, gap;
995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (p_pkt->offset < AVCT_MSG_OFFSET)
1015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
1025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        gap = AVCT_MSG_OFFSET - p_pkt->offset;
1035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        for(i=p_pkt->len; i>0; i--)
1045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
1055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            *(p_data + i + gap) = *(p_data + i);
1065738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
1075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_pkt->offset   += gap;
1085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_data          = (UINT8 *)(p_pkt+1) + p_pkt->offset;
1095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    *p_data         = AVRC_RSP_IMPL_STBL;
1115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    return p_data;
1125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
1135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1149adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan#if (AVRC_METADATA_INCLUDED == TRUE)
1159adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan/******************************************************************************
1169adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
1179adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan** Function         avrc_prep_end_frag
1189adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
1199adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan** Description      This function prepares an end response fragment
1209adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
1219adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan** Returns          Nothing.
1229adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
1239adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan******************************************************************************/
1249adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajanstatic void avrc_prep_end_frag(UINT8 handle)
1259adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan{
1269adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    tAVRC_FRAG_CB   *p_fcb;
1279adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    BT_HDR  *p_pkt_new;
1289adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT8   *p_data, *p_orig_data;
1299adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT8   rsp_type;
1309adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
1319adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    AVRC_TRACE_DEBUG0 ("avrc_prep_end_frag" );
1329adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    p_fcb = &avrc_cb.fcb[handle];
1339adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
1349adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    /* The response type of the end fragment should be the same as the the PDU of "End Fragment
1359adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    ** Respose" Errata: https://www.bluetooth.org/errata/errata_view.cfm?errata_id=4383 */
1369adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    p_orig_data = ((UINT8 *)(p_fcb->p_fmsg + 1) + p_fcb->p_fmsg->offset);
1379adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    rsp_type = ((*p_orig_data) & AVRC_CTYPE_MASK);
1389adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
1399adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    p_pkt_new           = p_fcb->p_fmsg;
1409adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    p_pkt_new->len      -= (AVRC_MAX_CTRL_DATA_LEN - AVRC_VENDOR_HDR_SIZE - AVRC_MIN_META_HDR_SIZE);
1419adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    p_pkt_new->offset   += (AVRC_MAX_CTRL_DATA_LEN - AVRC_VENDOR_HDR_SIZE - AVRC_MIN_META_HDR_SIZE);
1429adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    p_data = (UINT8 *)(p_pkt_new+1) + p_pkt_new->offset;
1439adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    *p_data++       = rsp_type;
1449adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    *p_data++       = (AVRC_SUB_PANEL << AVRC_SUBTYPE_SHIFT);
1459adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    *p_data++       = AVRC_OP_VENDOR;
1469adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    AVRC_CO_ID_TO_BE_STREAM(p_data, AVRC_CO_METADATA);
1479adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    *p_data++       = p_fcb->frag_pdu;
1489adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    *p_data++       = AVRC_PKT_END;
1499adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    /* 4=pdu, pkt_type & len */
1509adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT16_TO_BE_STREAM(p_data, (p_pkt_new->len - AVRC_VENDOR_HDR_SIZE - AVRC_MIN_META_HDR_SIZE));
1519adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan}
1529adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
1539adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan/******************************************************************************
1549adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
1559adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan** Function         avrc_send_continue_frag
1569adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
1579adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan** Description      This function sends a continue response fragment
1589adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
1599adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan** Returns          Nothing.
1609adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
1619adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan******************************************************************************/
1629adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajanstatic void avrc_send_continue_frag(UINT8 handle, UINT8 label)
1639adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan{
1649adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    tAVRC_FRAG_CB   *p_fcb;
1659adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    BT_HDR  *p_pkt_old, *p_pkt;
1669adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT8   *p_old, *p_data;
1679adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT8   cr = AVCT_RSP;
1689adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    tAVRC_RSP   rej_rsp;
1699adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
1709adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    p_fcb = &avrc_cb.fcb[handle];
1719adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    p_pkt = p_fcb->p_fmsg;
1729adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
1739adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    AVRC_TRACE_DEBUG1 ("avrc_send_continue_frag len(%d) / AVRC_MAX_CTRL_DATA_LEN", p_pkt->len );
1749adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    if (p_pkt->len > AVRC_MAX_CTRL_DATA_LEN)
1759adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    {
1769adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_pkt_old = p_fcb->p_fmsg;
1779adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_pkt = (BT_HDR *)GKI_getbuf((UINT16)(AVRC_PACKET_LEN + AVCT_MSG_OFFSET + BT_HDR_SIZE));
1789adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        if (p_pkt)
1799adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        {
1809adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_pkt->len          = AVRC_MAX_CTRL_DATA_LEN;
1819adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_pkt->offset       = AVCT_MSG_OFFSET;
1829adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_pkt->layer_specific = p_pkt_old->layer_specific;
1839adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_pkt->event = p_pkt_old->event;
1849adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_old = (UINT8 *)(p_pkt_old+1) + p_pkt_old->offset;
1859adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_data = (UINT8 *)(p_pkt+1) + p_pkt->offset;
1869adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            memcpy (p_data, p_old, AVRC_MAX_CTRL_DATA_LEN);
1879adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            /* use AVRC continue packet type */
1889adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_data += AVRC_VENDOR_HDR_SIZE;
1899adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_data++; /* pdu */
1909adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            *p_data++ = AVRC_PKT_CONTINUE;
1919adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            /* 4=pdu, pkt_type & len */
1929adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            UINT16_TO_BE_STREAM(p_data, (AVRC_MAX_CTRL_DATA_LEN - AVRC_VENDOR_HDR_SIZE - 4));
1939adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
1949adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            /* prepare the left over for as an end fragment */
1959adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            avrc_prep_end_frag (handle);
1969adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        }
1979adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        else
1989adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        {
1999adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            /* use the current GKI buffer to send Internal error status */
2009adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_pkt = p_fcb->p_fmsg;
2019adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_fcb->p_fmsg = NULL;
2029adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_fcb->frag_enabled = FALSE;
2039adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            AVRC_TRACE_ERROR0 ("AVRC_MsgReq no buffers for fragmentation - send internal error" );
2049adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_data = (UINT8 *)(p_pkt+1) + p_pkt->offset;
2059adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            *p_data++ = AVRC_PDU_REQUEST_CONTINUATION_RSP;
2069adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            *p_data++ = 0;
2079adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            UINT16_TO_BE_STREAM(p_data, 0);
2089adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_pkt->len = 4;
2099adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            rej_rsp.pdu = AVRC_PDU_REQUEST_CONTINUATION_RSP;
2109adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            rej_rsp.status = AVRC_STS_INTERNAL_ERR;
2119adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            AVRC_BldResponse( handle, (tAVRC_RESPONSE *)&rej_rsp, &p_pkt);
2129adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            cr = AVCT_RSP;
2139adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        }
2149adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    }
2159adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    else
2169adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    {
2179adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        /* end fragment. clean the control block */
2189adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_fcb->frag_enabled = FALSE;
2199adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_fcb->p_fmsg       = NULL;
2209adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    }
2219adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    AVCT_MsgReq( handle, label, cr, p_pkt);
2229adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan}
2239adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
2249adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan/******************************************************************************
2259adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
2269adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan** Function         avrc_proc_vendor_command
2279adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
2289adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan** Description      This function processes received vendor command.
2299adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
2309adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan** Returns          if not NULL, the response to send right away.
2319adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
2329adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan******************************************************************************/
2339adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajanstatic BT_HDR * avrc_proc_vendor_command(UINT8 handle, UINT8 label,
2349adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                               BT_HDR *p_pkt, tAVRC_MSG_VENDOR *p_msg)
2359adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan{
2369adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    BT_HDR      *p_rsp = NULL;
2379adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT8       *p_data;
2389adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT8       *p_begin;
2399adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT8       pkt_type;
2409adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    BOOLEAN     abort_frag = FALSE;
2419adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    tAVRC_STS   status = AVRC_STS_NO_ERROR;
2429adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    tAVRC_FRAG_CB   *p_fcb;
2439adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
2449adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    p_begin  = (UINT8 *)(p_pkt+1) + p_pkt->offset;
2459adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    p_data   = p_begin + AVRC_VENDOR_HDR_SIZE;
2469adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    pkt_type = *(p_data + 1) & AVRC_PKT_TYPE_MASK;
2479adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
2489adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    if (pkt_type != AVRC_PKT_SINGLE)
2499adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    {
2509adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        /* reject - commands can only be in single packets at AVRCP level */
2519adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        AVRC_TRACE_ERROR1 ("commands must be in single packet pdu:0x%x", *p_data );
2529adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        /* use the current GKI buffer to send the reject */
2539adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        status = AVRC_STS_BAD_CMD;
2549adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    }
2559adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    /* check if there are fragments waiting to be sent */
2569adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    else if (avrc_cb.fcb[handle].frag_enabled)
2579adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    {
2589adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_fcb = &avrc_cb.fcb[handle];
2599adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        if (p_msg->company_id == AVRC_CO_METADATA)
2609adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        {
2619adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            switch (*p_data)
2629adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            {
2639adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            case AVRC_PDU_ABORT_CONTINUATION_RSP:
2649adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                /* aborted by CT - send accept response */
2659adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                abort_frag = TRUE;
2669adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_begin = (UINT8 *)(p_pkt+1) + p_pkt->offset;
2679adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                *p_begin = (AVRC_RSP_ACCEPT & AVRC_CTYPE_MASK);
2689adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                if (*(p_data + 4) != p_fcb->frag_pdu)
2699adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                {
2709adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    *p_begin = (AVRC_RSP_REJ & AVRC_CTYPE_MASK);
2719adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    *(p_data + 4) = AVRC_STS_BAD_PARAM;
2729adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                }
2739adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                else
2749adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                {
2759adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_data = (p_begin + AVRC_VENDOR_HDR_SIZE + 2);
2769adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    UINT16_TO_BE_STREAM(p_data, 0);
2779adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_pkt->len = (p_data - p_begin);
2789adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                }
2799adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                AVCT_MsgReq( handle, label, AVCT_RSP, p_pkt);
2809adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_msg->hdr.opcode = AVRC_OP_DROP; /* used the p_pkt to send response */
2819adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                break;
2829adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
2839adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            case AVRC_PDU_REQUEST_CONTINUATION_RSP:
2849adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                if (*(p_data + 4) == p_fcb->frag_pdu)
2859adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                {
2869adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    avrc_send_continue_frag(handle, label);
2879adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_msg->hdr.opcode = AVRC_OP_DROP_N_FREE;
2889adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                }
2899adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                else
2909adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                {
2919adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    /* the pdu id does not match - reject the command using the current GKI buffer */
2929adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    AVRC_TRACE_ERROR2("avrc_proc_vendor_command continue pdu: 0x%x does not match \
2939adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    current re-assembly pdu: 0x%x",
2949adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                        *(p_data + 4), p_fcb->frag_pdu);
2959adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    status = AVRC_STS_BAD_PARAM;
2969adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    abort_frag = TRUE;
2979adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                }
2989adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                break;
2999adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
3009adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            default:
3019adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                /* implicit abort */
3029adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                abort_frag = TRUE;
3039adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            }
3049adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        }
3059adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        else
3069adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        {
3079adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            abort_frag = TRUE;
3089adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            /* implicit abort */
3099adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        }
3109adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
3119adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        if (abort_frag)
3129adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        {
3139adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            if (p_fcb->p_fmsg)
3149adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                GKI_freebuf(p_fcb->p_fmsg);
3159adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_fcb->p_fmsg = NULL;
3169adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_fcb->frag_enabled = FALSE;
3179adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        }
3189adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    }
3199adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
3209adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    if (status != AVRC_STS_NO_ERROR)
3219adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    {
3229adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        /* use the current GKI buffer to build/send the reject message */
3239adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_data = (UINT8 *)(p_pkt+1) + p_pkt->offset;
3249adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        *p_data++ = AVRC_RSP_REJ;
3259adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_data += AVRC_VENDOR_HDR_SIZE; /* pdu */
3269adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        *p_data++ = 0;                  /* pkt_type */
3279adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        UINT16_TO_BE_STREAM(p_data, 1); /* len */
3289adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        *p_data++ = status;             /* error code */
3299adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_pkt->len = AVRC_VENDOR_HDR_SIZE + 5;
3309adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_rsp = p_pkt;
3319adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    }
3329adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
3339adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    return p_rsp;
3349adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan}
3359adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
3369adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan/******************************************************************************
3379adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
3389adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan** Function         avrc_proc_far_msg
3399adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
3409adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan** Description      This function processes vendor command/response fragmetation
3419adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**                  and reassembly
3429adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
3439adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan** Returns          0, to report the message with msg_cback .
3449adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan**
3459adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan******************************************************************************/
3469adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajanstatic UINT8 avrc_proc_far_msg(UINT8 handle, UINT8 label, UINT8 cr, BT_HDR **pp_pkt,
3479adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    tAVRC_MSG_VENDOR *p_msg)
3489adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan{
3499adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    BT_HDR      *p_pkt = *pp_pkt;
3509adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT8       *p_data;
3519adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    BOOLEAN     drop = FALSE;
3529adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    BT_HDR      *p_rsp = NULL;
3539adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    BT_HDR      *p_cmd = NULL;
3549adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    BOOLEAN     req_continue = FALSE;
3559adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    BT_HDR      *p_pkt_new = NULL;
3569adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT8       pkt_type;
3579adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT16      buf_len;
3589adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    tAVRC_RASM_CB   *p_rcb;
3599adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    tAVRC_NEXT_CMD   avrc_cmd;
3609adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
3619adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    p_data  = (UINT8 *)(p_pkt+1) + p_pkt->offset;
3629adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    pkt_type = *(p_data + 1) & AVRC_PKT_TYPE_MASK;
3639adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    AVRC_TRACE_DEBUG1 ("pkt_type %d", pkt_type );
3649adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    p_rcb = &avrc_cb.rcb[handle];
3659adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    if (p_msg->company_id == AVRC_CO_METADATA)
3669adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    {
3679adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        /* check if the message needs to be re-assembled */
3689adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        if (pkt_type == AVRC_PKT_SINGLE || pkt_type == AVRC_PKT_START)
3699adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        {
3709adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            /* previous fragments need to be dropped, when received another new message */
3719adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_rcb->rasm_offset = 0;
3729adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            if (p_rcb->p_rmsg)
3739adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            {
3749adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                GKI_freebuf(p_rcb->p_rmsg);
3759adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_rcb->p_rmsg = NULL;
3769adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            }
3779adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        }
3789adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
3799adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        if (pkt_type != AVRC_PKT_SINGLE && cr == AVCT_RSP)
3809adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        {
3819adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            /* not a single response packet - need to re-assemble metadata messages */
3829adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            if (pkt_type == AVRC_PKT_START)
3839adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            {
3849adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_rcb->rasm_offset = p_pkt->offset;
3859adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_rcb->p_rmsg = p_pkt;
3869adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                /* set offset to point to where to copy next - use the same re-asm logic as AVCT */
3879adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_rcb->p_rmsg->offset += p_rcb->p_rmsg->len;
3889adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_rcb->rasm_pdu = *p_data;
3899adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                req_continue = TRUE;
3909adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            }
3919adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            else
3929adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            {
3939adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                /* get size of buffer holding assembled message */
3949adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                buf_len = GKI_get_buf_size (p_rcb->p_rmsg) - sizeof(BT_HDR);
3959adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                /* adjust offset and len of fragment for header byte */
3969adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_pkt->offset += (AVRC_VENDOR_HDR_SIZE + AVRC_MIN_META_HDR_SIZE);
3979adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_pkt->len -= (AVRC_VENDOR_HDR_SIZE + AVRC_MIN_META_HDR_SIZE);
3989adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                /* verify length */
3999adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                if ((p_rcb->p_rmsg->offset + p_pkt->len) > buf_len)
4009adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                {
4019adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    AVRC_TRACE_WARNING0("Fragmented message too big! - report the partial message");
4029adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_pkt->len = buf_len - p_rcb->p_rmsg->offset;
4039adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    pkt_type = AVRC_PKT_END;
4049adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                }
4059adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
4069adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                /* copy contents of p_pkt to p_rx_msg */
4079adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                memcpy((UINT8 *)(p_rcb->p_rmsg + 1) + p_rcb->p_rmsg->offset,
4089adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                       (UINT8 *)(p_pkt + 1) + p_pkt->offset, p_pkt->len);
4099adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
4109adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                if (pkt_type == AVRC_PKT_END)
4119adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                {
4129adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_rcb->p_rmsg->offset = p_rcb->rasm_offset;
4139adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_rcb->p_rmsg->len += p_pkt->len;
4149adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_pkt_new = p_rcb->p_rmsg;
4159adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_rcb->rasm_offset = 0;
4169adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_rcb->p_rmsg = NULL;
4179adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_msg->p_vendor_data   = (UINT8 *)(p_pkt_new+1) + p_pkt_new->offset;
4189adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_msg->hdr.ctype       = p_msg->p_vendor_data[0] & AVRC_CTYPE_MASK;
4199adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    /* 6 = ctype, subunit*, opcode & CO_ID */
4209adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_msg->p_vendor_data  += AVRC_VENDOR_HDR_SIZE;
4219adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_msg->vendor_len      = p_pkt_new->len - AVRC_VENDOR_HDR_SIZE;
4229adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_data = p_msg->p_vendor_data + 1; /* skip pdu */
4239adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    *p_data++ = AVRC_PKT_SINGLE;
4249adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    UINT16_TO_BE_STREAM(p_data, (p_msg->vendor_len - AVRC_MIN_META_HDR_SIZE));
4259adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    AVRC_TRACE_DEBUG3("end frag:%d, total len:%d, offset:%d", p_pkt->len,
4269adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                        p_pkt_new->len, p_pkt_new->offset);
4279adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                }
4289adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                else
4299adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                {
4309adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_rcb->p_rmsg->offset += p_pkt->len;
4319adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_rcb->p_rmsg->len += p_pkt->len;
4329adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_pkt_new = NULL;
4339adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    req_continue = TRUE;
4349adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                }
4359adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                GKI_freebuf(p_pkt);
4369adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                *pp_pkt = p_pkt_new;
4379adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            }
4389adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        }
4399adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
4409adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        if (cr == AVCT_CMD)
4419adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        {
4429adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_rsp = avrc_proc_vendor_command(handle, label, *pp_pkt, p_msg);
4439adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            if (p_rsp)
4449adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            {
4459adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                AVCT_MsgReq( handle, label, AVCT_RSP, p_rsp);
4469adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                drop = 3;
4479adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            }
4489adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            else if (p_msg->hdr.opcode == AVRC_OP_DROP)
4499adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            {
4509adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                drop = 1;
4519adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            }
4529adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            else if (p_msg->hdr.opcode == AVRC_OP_DROP_N_FREE)
4539adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                drop = 4;
4549adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
4559adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        }
4569adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    }
4579adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    return drop;
4589adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan}
4599adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan#endif /* (AVRC_METADATA_INCLUDED == TRUE) */
4605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
4625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
4635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         avrc_msg_cback
4645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
4655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This is the callback function used by AVCTP to report
4665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  received AV control messages.
4675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
4685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          Nothing.
4695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
4705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project******************************************************************************/
4715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void avrc_msg_cback(UINT8 handle, UINT8 label, UINT8 cr,
4725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                               BT_HDR *p_pkt)
4735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
4745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8       opcode;
4755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tAVRC_MSG   msg;
4765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8       *p_data;
4775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8       *p_begin;
4785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    BOOLEAN     drop = FALSE;
4795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    BOOLEAN     free = TRUE;
4805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    BT_HDR      *p_rsp = NULL;
4815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8       *p_rsp_data;
4825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    int         xx;
4835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    BOOLEAN     reject = FALSE;
4845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#if (BT_USE_TRACES == TRUE)
4855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    char        *p_drop_msg = "dropped";
4865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#endif
4875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tAVRC_MSG_VENDOR *p_msg = &msg.vendor;
4885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (cr == AVCT_CMD &&
4905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        (p_pkt->layer_specific & AVCT_DATA_CTRL && AVRC_PACKET_LEN < sizeof(p_pkt->len)))
4915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
4925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        /* Ignore the invalid AV/C command frame */
4935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#if (BT_USE_TRACES == TRUE)
4945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_drop_msg = "dropped - too long AV/C cmd frame size";
4955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#endif
4965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        GKI_freebuf(p_pkt);
4975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return;
4985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
4995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (cr == AVCT_REJ)
5015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
5025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        /* The peer thinks that this PID is no longer open - remove this handle */
5035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        /*  */
5045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        GKI_freebuf(p_pkt);
5055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        AVCT_RemoveConn(handle);
5065738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return;
5075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
5085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_data  = (UINT8 *)(p_pkt+1) + p_pkt->offset;
5105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    memset(&msg, 0, sizeof(tAVRC_MSG) );
5115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
5125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        msg.hdr.ctype           = p_data[0] & AVRC_CTYPE_MASK;
5135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        AVRC_TRACE_DEBUG4("avrc_msg_cback handle:%d, ctype:%d, offset:%d, len: %d",
5145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                handle, msg.hdr.ctype, p_pkt->offset, p_pkt->len);
5155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        msg.hdr.subunit_type    = (p_data[1] & AVRC_SUBTYPE_MASK) >> AVRC_SUBTYPE_SHIFT;
5165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        msg.hdr.subunit_id      = p_data[1] & AVRC_SUBID_MASK;
5175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        opcode                  = p_data[2];
5185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
5195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if ( ((avrc_cb.ccb[handle].control & AVRC_CT_TARGET) && (cr == AVCT_CMD)) ||
5215738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        ((avrc_cb.ccb[handle].control & AVRC_CT_CONTROL) && (cr == AVCT_RSP)) )
5225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
5235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        switch(opcode)
5255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
5265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        case AVRC_OP_UNIT_INFO:
5275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            if (cr == AVCT_CMD)
5285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            {
5295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                /* send the response to the peer */
5305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                p_rsp           = p_pkt; /* this also sets free = FALSE, drop = TRUE */
5315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                /* check & set the offset. set response code, set subunit_type & subunit_id,
5325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                   set AVRC_OP_UNIT_INFO */
5339adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                /* 3 bytes: ctype, subunit*, opcode */
5349adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_rsp_data      = avrc_get_data_ptr(p_pkt) + AVRC_AVC_HDR_SIZE;
5355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                *p_rsp_data++   = 7;
5365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                /* Panel subunit & id=0 */
5375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                *p_rsp_data++   = (AVRC_SUB_PANEL << AVRC_SUBTYPE_SHIFT);
5385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                AVRC_CO_ID_TO_BE_STREAM(p_rsp_data, avrc_cb.ccb[handle].company_id);
5395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                p_rsp->len      = (UINT16) (p_rsp_data - (UINT8 *)(p_rsp + 1) - p_rsp->offset);
5405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                cr = AVCT_RSP;
5415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#if (BT_USE_TRACES == TRUE)
5425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                p_drop_msg = "auto respond";
5435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#endif
5445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            }
5455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            else
5465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            {
5475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                /* parse response */
5485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                p_data += 4; /* 3 bytes: ctype, subunit*, opcode + octet 3 (is 7)*/
5495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                msg.unit.unit_type  = (*p_data & AVRC_SUBTYPE_MASK) >> AVRC_SUBTYPE_SHIFT;
5505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                msg.unit.unit       = *p_data & AVRC_SUBID_MASK;
5515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                p_data++;
5525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                AVRC_BE_STREAM_TO_CO_ID(msg.unit.company_id, p_data);
5535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            }
5545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            break;
5555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        case AVRC_OP_SUB_INFO:
5575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            if (cr == AVCT_CMD)
5585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            {
5595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                /* send the response to the peer */
5605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                p_rsp           = p_pkt; /* this also sets free = FALSE, drop = TRUE */
5615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                /* check & set the offset. set response code, set (subunit_type & subunit_id),
5625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                   set AVRC_OP_SUB_INFO, set (page & extention code) */
5635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                p_rsp_data      = avrc_get_data_ptr(p_pkt) + 4;
5645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                /* Panel subunit & id=0 */
5655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                *p_rsp_data++   = (AVRC_SUB_PANEL << AVRC_SUBTYPE_SHIFT);
5665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                memset(p_rsp_data, AVRC_CMD_OPRND_PAD, AVRC_SUBRSP_OPRND_BYTES);
5675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                p_rsp_data      += AVRC_SUBRSP_OPRND_BYTES;
5685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                p_rsp->len      = (UINT16) (p_rsp_data - (UINT8 *)(p_rsp + 1) - p_rsp->offset);
5695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                cr = AVCT_RSP;
5705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#if (BT_USE_TRACES == TRUE)
5715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                p_drop_msg = "auto responded";
5725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#endif
5735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            }
5745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            else
5755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            {
5765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                /* parse response */
5775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                p_data += AVRC_AVC_HDR_SIZE; /* 3 bytes: ctype, subunit*, opcode */
5785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                msg.sub.page    = (*p_data++ >> AVRC_SUB_PAGE_SHIFT) & AVRC_SUB_PAGE_MASK;
5795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                xx      = 0;
5805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                while (*p_data != AVRC_CMD_OPRND_PAD && xx<AVRC_SUB_TYPE_LEN)
5815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                {
5825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                    msg.sub.subunit_type[xx] = *p_data++ >> AVRC_SUBTYPE_SHIFT;
5835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                    if (msg.sub.subunit_type[xx] == AVRC_SUB_PANEL)
5845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                        msg.sub.panel   = TRUE;
5855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                    xx++;
5865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                }
5875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            }
5885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            break;
5895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        case AVRC_OP_VENDOR:
5915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            p_data  = (UINT8 *)(p_pkt+1) + p_pkt->offset;
5925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            p_begin = p_data;
5935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            if (p_pkt->len < AVRC_VENDOR_HDR_SIZE) /* 6 = ctype, subunit*, opcode & CO_ID */
5945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            {
5955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                if (cr == AVCT_CMD)
5965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                    reject = TRUE;
5975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                else
5985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                    drop = TRUE;
5995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                break;
6005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            }
6015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            p_data += AVRC_AVC_HDR_SIZE; /* skip the first 3 bytes: ctype, subunit*, opcode */
6025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            AVRC_BE_STREAM_TO_CO_ID(p_msg->company_id, p_data);
6035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            p_msg->p_vendor_data   = p_data;
6045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            p_msg->vendor_len      = p_pkt->len - (p_data - p_begin);
6055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6069adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan#if (AVRC_METADATA_INCLUDED == TRUE)
6079adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            drop = avrc_proc_far_msg(handle, label, cr, &p_pkt, p_msg);
6089adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            if (drop)
6099adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            {
6109adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                free = FALSE;
6119adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                if (drop == 4)
6129adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    free = TRUE;
6139adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan#if (BT_USE_TRACES == TRUE)
6149adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                switch (drop)
6159adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                {
6169adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                case 1:
6179adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_drop_msg = "sent_frag";
6189adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    break;
6199adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                case 2:
6209adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_drop_msg = "req_cont";
6219adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    break;
6229adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                case 3:
6239adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_drop_msg = "sent_frag3";
6249adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    break;
6259adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                case 4:
6269adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_drop_msg = "sent_frag_free";
6279adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    break;
6289adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                default:
6299adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                    p_drop_msg = "sent_fragd";
6309adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                }
6319adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan#endif
6329adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            }
6339adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan#endif /* (AVRC_METADATA_INCLUDED == TRUE) */
6345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            break;
6355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        case AVRC_OP_PASS_THRU:
6375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            if (p_pkt->len < 5) /* 3 bytes: ctype, subunit*, opcode & op_id & len */
6385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            {
6395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                if (cr == AVCT_CMD)
6405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                    reject = TRUE;
6415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                else
6425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                    drop = TRUE;
6435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                break;
6445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            }
6455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            p_data += AVRC_AVC_HDR_SIZE; /* skip the first 3 bytes: ctype, subunit*, opcode */
6465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            msg.pass.op_id  = (AVRC_PASS_OP_ID_MASK & *p_data);
6475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            if (AVRC_PASS_STATE_MASK & *p_data)
6485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                msg.pass.state  = TRUE;
6495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            else
6505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                msg.pass.state  = FALSE;
6515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            p_data++;
6525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            msg.pass.pass_len    = *p_data++;
6535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            if (msg.pass.pass_len != p_pkt->len - 5)
6545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                msg.pass.pass_len = p_pkt->len - 5;
6555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            if (msg.pass.pass_len)
6565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                msg.pass.p_pass_data = p_data;
6575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            else
6585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                msg.pass.p_pass_data = NULL;
6595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            break;
6605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        default:
6635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            if ((avrc_cb.ccb[handle].control & AVRC_CT_TARGET) && (cr == AVCT_CMD))
6645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            {
6655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                /* reject unsupported opcode */
6665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                reject = TRUE;
6675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            }
6685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            drop    = TRUE;
6695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            break;
6705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
6715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
6725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    else /* drop the event */
6735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
6745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            drop    = TRUE;
6755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
6765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (reject)
6785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
6795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        /* reject unsupported opcode */
6805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_rsp           = p_pkt; /* this also sets free = FALSE, drop = TRUE */
6815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_rsp_data      = avrc_get_data_ptr(p_pkt);
6825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        *p_rsp_data     = AVRC_RSP_REJ;
6835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#if (BT_USE_TRACES == TRUE)
6845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_drop_msg = "rejected";
6855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#endif
6865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        cr      = AVCT_RSP;
6875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        drop    = TRUE;
6885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
6895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (p_rsp)
6915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
6925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        /* set to send response right away */
6935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        AVCT_MsgReq( handle, label, cr, p_rsp);
6945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        free = FALSE;
6955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        drop = TRUE;
6965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
6975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (drop == FALSE)
6995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
7005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        msg.hdr.opcode = opcode;
7015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        (*avrc_cb.ccb[handle].p_msg_cback)(handle, label, opcode, &msg);
7025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
7035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#if (BT_USE_TRACES == TRUE)
7045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    else
7055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
7065738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        AVRC_TRACE_WARNING5("avrc_msg_cback %s msg handle:%d, control:%d, cr:%d, opcode:x%x",
7075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                p_drop_msg,
7085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                handle, avrc_cb.ccb[handle].control, cr, opcode);
7095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
7105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#endif
7115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (free)
7145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        GKI_freebuf(p_pkt);
7155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
7165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
7215738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         avrc_pass_msg
7235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      Compose a PASS THROUGH command according to p_msg
7255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  Input Parameters:
7275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      p_msg: Pointer to PASS THROUGH message structure.
7285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  Output Parameters:
7305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      None.
7315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          pointer to a valid GKI buffer if successful.
7335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  NULL if p_msg is NULL.
7345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project******************************************************************************/
7365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic BT_HDR  * avrc_pass_msg(tAVRC_MSG_PASS *p_msg)
7375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
7385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    BT_HDR  *p_cmd = NULL;
7395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8   *p_data;
7405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    WC_ASSERT(p_msg != NULL);
7425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    WC_ASSERT(AVRC_CMD_POOL_SIZE > (AVRC_MIN_CMD_LEN+p_msg->pass_len));
7435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if ((p_cmd = (BT_HDR *) GKI_getpoolbuf(AVRC_CMD_POOL_ID)) != NULL)
7455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
7465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_cmd->offset   = AVCT_MSG_OFFSET;
7475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_cmd->layer_specific   = AVCT_DATA_CTRL;
7485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_data          = (UINT8 *)(p_cmd + 1) + p_cmd->offset;
7495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        *p_data++       = (p_msg->hdr.ctype & AVRC_CTYPE_MASK);
7505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        *p_data++       = (AVRC_SUB_PANEL << AVRC_SUBTYPE_SHIFT); /* Panel subunit & id=0 */
7515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        *p_data++       = AVRC_OP_PASS_THRU;
7525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        *p_data         = (AVRC_PASS_OP_ID_MASK&p_msg->op_id);
7535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if (p_msg->state)
7545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            *p_data     |= AVRC_PASS_STATE_MASK;
7555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_data++;
7565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if (p_msg->op_id == AVRC_ID_VENDOR)
7585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
7595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            *p_data++       = p_msg->pass_len;
7605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            if (p_msg->pass_len && p_msg->p_pass_data)
7615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            {
7625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                memcpy(p_data, p_msg->p_pass_data, p_msg->pass_len);
7635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                p_data += p_msg->pass_len;
7645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            }
7655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
7665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        else /* set msg len to 0 for other op_id */
7675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
7685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            /* set msg len to 0 for other op_id */
7695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            *p_data++       = 0;
7705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
7715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_cmd->len      = (UINT16) (p_data - (UINT8 *)(p_cmd + 1) - p_cmd->offset);
7725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
7735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    return p_cmd;
7745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
7755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
7775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         AVRC_Open
7795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function is called to open a connection to AVCTP.
7815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  The connection can be either an initiator or acceptor, as
7825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  determined by the p_ccb->stream parameter.
7835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  The connection can be a target, a controller or for both role,
7845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  as determined by the p_ccb->control parameter.
7855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  By definition, a target connection is an acceptor connection
7865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  that waits for an incoming AVCTP connection from the peer.
7875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  The connection remains available to the application until
7885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  the application closes it by calling AVRC_Close().  The
7895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  application does not need to reopen the connection after an
7905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  AVRC_CLOSE_IND_EVT is received.
7915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  Input Parameters:
7935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      p_ccb->company_id: Company Identifier.
7945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      p_ccb->p_ctrl_cback:  Pointer to control callback function.
7965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      p_ccb->p_msg_cback:  Pointer to message callback function.
7985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      p_ccb->conn: AVCTP connection role.  This is set to
8005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      AVCTP_INT for initiator connections and AVCTP_ACP
8015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      for acceptor connections.
8025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      p_ccb->control: Control role.  This is set to
8045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      AVRC_CT_TARGET for target connections, AVRC_CT_CONTROL
8055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      for control connections or (AVRC_CT_TARGET|AVRC_CT_CONTROL)
8065738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      for connections that support both roles.
8075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      peer_addr: BD address of peer device.  This value is
8095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      only used for initiator connections; for acceptor
8105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      connections it can be set to NULL.
8115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  Output Parameters:
8135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      p_handle: Pointer to handle.  This parameter is only
8145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                                valid if AVRC_SUCCESS is returned.
8155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          AVRC_SUCCESS if successful.
8175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  AVRC_NO_RESOURCES if there are not enough resources to open
8185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  the connection.
8195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project******************************************************************************/
8215738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source ProjectUINT16 AVRC_Open(UINT8 *p_handle, tAVRC_CONN_CB *p_ccb, BD_ADDR_PTR peer_addr)
8225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
8235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT16      status;
8245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tAVCT_CC    cc;
8255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    cc.p_ctrl_cback = avrc_ctrl_cback;      /* Control callback */
8275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    cc.p_msg_cback  = avrc_msg_cback;       /* Message callback */
8285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    cc.pid          = UUID_SERVCLASS_AV_REMOTE_CONTROL;  /* Profile ID */
8295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    cc.role         = p_ccb->conn;          /* Initiator/acceptor role */
8305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    cc.control      = p_ccb->control;       /* Control role (Control/Target) */
8315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    status = AVCT_CreateConn(p_handle, &cc, peer_addr);
8335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (status == AVCT_SUCCESS)
8345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
8355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        memcpy(&avrc_cb.ccb[*p_handle], p_ccb, sizeof(tAVRC_CONN_CB));
8369adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan#if (AVRC_METADATA_INCLUDED == TRUE)
8379adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        memset(&avrc_cb.fcb[*p_handle], 0, sizeof(tAVRC_FRAG_CB));
8389adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        memset(&avrc_cb.rcb[*p_handle], 0, sizeof(tAVRC_RASM_CB));
8399adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan#endif
8405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
8419adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    AVRC_TRACE_DEBUG4("AVRC_Open role: %d, control:%d status:%d, handle:%d", cc.role, cc.control,
8429adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        status, *p_handle);
8435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    return status;
8455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
8465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
8485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         AVRC_Close
8505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      Close a connection opened with AVRC_Open().
8525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  This function is called when the
8535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  application is no longer using a connection.
8545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  Input Parameters:
8565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      handle: Handle of this connection.
8575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  Output Parameters:
8595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      None.
8605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          AVRC_SUCCESS if successful.
8625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  AVRC_BAD_HANDLE if handle is invalid.
8635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project******************************************************************************/
8655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source ProjectUINT16 AVRC_Close(UINT8 handle)
8665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
8675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    AVRC_TRACE_DEBUG1("AVRC_Close handle:%d", handle);
8685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    return AVCT_RemoveConn(handle);
8695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
8705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
8735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         AVRC_MsgReq
8755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function is used to send the AVRCP byte stream in p_pkt
8775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  down to AVCTP.
8785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  It is expected that p_pkt->offset is at least AVCT_MSG_OFFSET
8805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  p_pkt->layer_specific is AVCT_DATA_CTRL or AVCT_DATA_BROWSE
8815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  p_pkt->event is AVRC_OP_VENDOR, AVRC_OP_PASS_THRU or AVRC_OP_BROWSE
8825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  The above BT_HDR settings are set by the AVRC_Bld* functions.
8835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          AVRC_SUCCESS if successful.
8855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  AVRC_BAD_HANDLE if handle is invalid.
8865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project******************************************************************************/
8885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source ProjectUINT16 AVRC_MsgReq (UINT8 handle, UINT8 label, UINT8 ctype, BT_HDR *p_pkt)
8895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
8909adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan#if (AVRC_METADATA_INCLUDED == TRUE)
8919adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT8   *p_data;
8929adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT8   cr = AVCT_CMD;
8939adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    BOOLEAN chk_frag = TRUE;
8949adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT8   *p_start = NULL;
8959adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    tAVRC_FRAG_CB   *p_fcb;
8969adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    UINT16  len;
8979adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    BT_HDR  *p_pkt_new;
8989adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
8999adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    if (!p_pkt)
9009adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        return AVRC_BAD_PARAM;
9019adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
9029adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    if (ctype >= AVRC_RSP_NOT_IMPL)
9039adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        cr = AVCT_RSP;
9049adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
9059adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    if (p_pkt->event == AVRC_OP_VENDOR)
9069adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    {
9079adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        /* add AVRCP Vendor Dependent headers */
9089adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_start = ((UINT8 *)(p_pkt + 1) + p_pkt->offset);
9099adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_pkt->offset -= AVRC_VENDOR_HDR_SIZE;
9109adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_pkt->len += AVRC_VENDOR_HDR_SIZE;
9119adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_data = (UINT8 *)(p_pkt + 1) + p_pkt->offset;
9129adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        *p_data++       = (ctype & AVRC_CTYPE_MASK);
9139adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        *p_data++       = (AVRC_SUB_PANEL << AVRC_SUBTYPE_SHIFT);
9149adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        *p_data++       = AVRC_OP_VENDOR;
9159adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        AVRC_CO_ID_TO_BE_STREAM(p_data, AVRC_CO_METADATA);
9169adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    }
9179adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    else if (p_pkt->event == AVRC_OP_PASS_THRU)
9189adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    {
9199adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        /* add AVRCP Pass Through headers */
9209adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_start = ((UINT8 *)(p_pkt + 1) + p_pkt->offset);
9219adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_pkt->offset -= AVRC_PASS_THRU_SIZE;
9229adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_pkt->len += AVRC_PASS_THRU_SIZE;
9239adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_data = (UINT8 *)(p_pkt + 1) + p_pkt->offset;
9249adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        *p_data++       = (ctype & AVRC_CTYPE_MASK);
9259adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        *p_data++       = (AVRC_SUB_PANEL << AVRC_SUBTYPE_SHIFT);
9269adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        *p_data++       = AVRC_OP_PASS_THRU;/* opcode */
9279adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        *p_data++       = AVRC_ID_VENDOR;   /* operation id */
9289adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        *p_data++       = 5;                /* operation data len */
9299adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        AVRC_CO_ID_TO_BE_STREAM(p_data, AVRC_CO_METADATA);
9309adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    }
9319adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
9329adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    /* abandon previous fragments */
9339adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    p_fcb = &avrc_cb.fcb[handle];
9349adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    if (p_fcb->frag_enabled)
9359adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_fcb->frag_enabled = FALSE;
9369adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
9379adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    if (p_fcb->p_fmsg)
9389adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    {
9399adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        GKI_freebuf(p_fcb->p_fmsg);
9409adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        p_fcb->p_fmsg = NULL;
9419adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    }
9429adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
9439adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    /* AVRCP spec has not defined any control channel commands that needs fragmentation at this level
9449adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan     * check for fragmentation only on the response */
9459adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    if ((cr == AVCT_RSP) && (chk_frag == TRUE))
9469adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    {
9479adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        if (p_pkt->len > AVRC_MAX_CTRL_DATA_LEN)
9489adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        {
9499adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            AVRC_TRACE_DEBUG1 ("p_pkt->len(%d) > AVRC_MAX_CTRL_DATA_LEN", p_pkt->len );
9509adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            p_pkt_new = (BT_HDR *)GKI_getbuf((UINT16)(AVRC_PACKET_LEN + AVCT_MSG_OFFSET
9519adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                + BT_HDR_SIZE));
9529adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            if (p_pkt_new)
9539adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            {
9549adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_fcb->frag_enabled = TRUE;
9559adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_fcb->p_fmsg       = p_pkt;
9569adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_fcb->frag_pdu     = *p_start;
9579adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_pkt               = p_pkt_new;
9589adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_pkt_new           = p_fcb->p_fmsg;
9599adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_pkt->len          = AVRC_MAX_CTRL_DATA_LEN;
9609adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_pkt->offset       = p_pkt_new->offset;
9619adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_pkt->layer_specific = p_pkt_new->layer_specific;
9629adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_pkt->event = p_pkt_new->event;
9639adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_data = (UINT8 *)(p_pkt+1) + p_pkt->offset;
9649adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_start -= AVRC_VENDOR_HDR_SIZE;
9659adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                memcpy (p_data, p_start, AVRC_MAX_CTRL_DATA_LEN);
9669adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                /* use AVRC start packet type */
9679adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_data += AVRC_VENDOR_HDR_SIZE;
9689adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                p_data++; /* pdu */
9699adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                *p_data++ = AVRC_PKT_START;
9709adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                /* 4 pdu, pkt_type & len */
9719adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                len = (AVRC_MAX_CTRL_DATA_LEN - AVRC_VENDOR_HDR_SIZE - AVRC_MIN_META_HDR_SIZE);
9729adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                UINT16_TO_BE_STREAM(p_data, len);
9739adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
9749adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                /* prepare the left over for as an end fragment */
9759adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                avrc_prep_end_frag (handle);
9769adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                AVRC_TRACE_DEBUG3 ("p_pkt len:%d/%d, next len:%d", p_pkt->len, len, p_fcb->p_fmsg->len );
9779adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            }
9789adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            else
9799adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan            {
9809adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                AVRC_TRACE_ERROR0 ("AVRC_MsgReq no buffers for fragmentation" );
9819adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan                GKI_freebuf(p_pkt);
9825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    return AVRC_NO_RESOURCES;
9835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
9849adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan        }
9859adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    }
9869adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan
9879adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    return AVCT_MsgReq( handle, label, cr, p_pkt);
9889adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan#else
9899adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan    return AVRC_NO_RESOURCES;
9909adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan#endif
9919adddf4965e9ddb01e339b934c343fcbd842a977Ravi Nagarajan}
9925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
9955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
9965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         AVRC_PassCmd
9975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
9985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      Send a PASS THROUGH command to the peer device.  This
9995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  function can only be called for controller role connections.
10005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  Any response message from the peer is passed back through
10015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  the tAVRC_MSG_CBACK callback function.
10025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  Input Parameters:
10045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      handle: Handle of this connection.
10055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10065738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      label: Transaction label.
10075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      p_msg: Pointer to PASS THROUGH message structure.
10095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  Output Parameters:
10115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      None.
10125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          AVRC_SUCCESS if successful.
10145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  AVRC_BAD_HANDLE if handle is invalid.
10155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project******************************************************************************/
10175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source ProjectUINT16 AVRC_PassCmd(UINT8 handle, UINT8 label, tAVRC_MSG_PASS *p_msg)
10185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
10195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    BT_HDR *p_buf;
10205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    WC_ASSERT(p_msg != NULL);
10215738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (p_msg)
10225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
10235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_msg->hdr.ctype    = AVRC_CMD_CTRL;
10245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_buf = avrc_pass_msg(p_msg);
10255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if (p_buf)
10265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            return AVCT_MsgReq( handle, label, AVCT_CMD, p_buf);
10275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
10285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    return AVRC_NO_RESOURCES;
10295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
10305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
10325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         AVRC_PassRsp
10345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      Send a PASS THROUGH response to the peer device.  This
10365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  function can only be called for target role connections.
10375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  This function must be called when a PASS THROUGH command
10385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  message is received from the peer through the
10395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  tAVRC_MSG_CBACK callback function.
10405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  Input Parameters:
10425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      handle: Handle of this connection.
10435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      label: Transaction label.  Must be the same value as
10455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      passed with the command message in the callback function.
10465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      p_msg: Pointer to PASS THROUGH message structure.
10485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  Output Parameters:
10505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                      None.
10515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          AVRC_SUCCESS if successful.
10535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  AVRC_BAD_HANDLE if handle is invalid.
10545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project******************************************************************************/
10565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source ProjectUINT16 AVRC_PassRsp(UINT8 handle, UINT8 label, tAVRC_MSG_PASS *p_msg)
10575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
10585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    BT_HDR *p_buf;
10595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    WC_ASSERT(p_msg != NULL);
10605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (p_msg)
10615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
10625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_buf = avrc_pass_msg(p_msg);
10635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if (p_buf)
10645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            return AVCT_MsgReq( handle, label, AVCT_RSP, p_buf);
10655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
10665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    return AVRC_NO_RESOURCES;
10675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
10685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1069