1 /******************************************************************************
2  *
3  *  Copyright (C) 2002-2012 Broadcom Corporation
4  *
5  *  Licensed under the Apache License, Version 2.0 (the "License");
6  *  you may not use this file except in compliance with the License.
7  *  You may obtain a copy of the License at:
8  *
9  *  http://www.apache.org/licenses/LICENSE-2.0
10  *
11  *  Unless required by applicable law or agreed to in writing, software
12  *  distributed under the License is distributed on an "AS IS" BASIS,
13  *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  *  See the License for the specific language governing permissions and
15  *  limitations under the License.
16  *
17  ******************************************************************************/
18 
19 /******************************************************************************
20  *
21  *  This module contains API of the audio/video distribution transport
22  *  protocol.
23  *
24  ******************************************************************************/
25 
26 #include <string.h>
27 #include "stack/bt_types.h"
28 #include "common/bt_target.h"
29 #include "stack/avdt_api.h"
30 #include "stack/avdtc_api.h"
31 #include "avdt_int.h"
32 #include "stack/l2c_api.h"
33 #include "stack/btm_api.h"
34 #include "stack/btu.h"
35 #include "osi/allocator.h"
36 
37 #if (defined(AVDT_INCLUDED) && AVDT_INCLUDED == TRUE)
38 
39 /* Control block for AVDT */
40 #if AVDT_DYNAMIC_MEMORY == FALSE
41 tAVDT_CB avdt_cb;
42 #else
43 tAVDT_CB *avdt_cb_ptr;
44 #endif
45 
46 /*******************************************************************************
47 **
48 ** Function         avdt_process_timeout
49 **
50 ** Description      This function is called by BTU when an AVDTP timer
51 **                  expires.  The function sends a timer event to the
52 **                  appropriate CCB or SCB state machine.
53 **
54 **                  This function is for use internal to the stack only.
55 **
56 **
57 ** Returns          void
58 **
59 *******************************************************************************/
avdt_process_timeout(TIMER_LIST_ENT * p_tle)60 void avdt_process_timeout(TIMER_LIST_ENT *p_tle)
61 {
62     UINT8   event = 0;
63     UINT8   err_code = AVDT_ERR_TIMEOUT;
64 
65     switch (p_tle->event) {
66     case BTU_TTYPE_AVDT_CCB_RET:
67         event = AVDT_CCB_RET_TOUT_EVT + AVDT_CCB_MKR;
68         break;
69 
70     case BTU_TTYPE_AVDT_CCB_RSP:
71         event = AVDT_CCB_RSP_TOUT_EVT + AVDT_CCB_MKR;
72         break;
73 
74     case BTU_TTYPE_AVDT_CCB_IDLE:
75         event = AVDT_CCB_IDLE_TOUT_EVT + AVDT_CCB_MKR;
76         break;
77 
78     case BTU_TTYPE_AVDT_SCB_TC:
79         event = AVDT_SCB_TC_TOUT_EVT;
80         break;
81 
82     default:
83         break;
84     }
85 
86     if (event & AVDT_CCB_MKR) {
87         avdt_ccb_event((tAVDT_CCB *) p_tle->param, (UINT8) (event & ~AVDT_CCB_MKR),
88                        (tAVDT_CCB_EVT *) &err_code);
89     } else {
90         avdt_scb_event((tAVDT_SCB *) p_tle->param, event, NULL);
91     }
92 }
93 
94 /*******************************************************************************
95 **
96 ** Function         AVDT_Register
97 **
98 ** Description      This is the system level registration function for the
99 **                  AVDTP protocol.  This function initializes AVDTP and
100 **                  prepares the protocol stack for its use.  This function
101 **                  must be called once by the system or platform using AVDTP
102 **                  before the other functions of the API an be used.
103 **
104 **
105 ** Returns          void
106 **
107 *******************************************************************************/
AVDT_Register(tAVDT_REG * p_reg,tAVDT_CTRL_CBACK * p_cback)108 void AVDT_Register(tAVDT_REG *p_reg, tAVDT_CTRL_CBACK *p_cback)
109 {
110     /* register PSM with L2CAP */
111     L2CA_Register(AVDT_PSM, (tL2CAP_APPL_INFO *) &avdt_l2c_appl);
112 
113     /* set security level */
114     BTM_SetSecurityLevel(TRUE, "", BTM_SEC_SERVICE_AVDTP, p_reg->sec_mask,
115                          AVDT_PSM, BTM_SEC_PROTO_AVDT, AVDT_CHAN_SIG);
116     BTM_SetSecurityLevel(FALSE, "", BTM_SEC_SERVICE_AVDTP, p_reg->sec_mask,
117                          AVDT_PSM, BTM_SEC_PROTO_AVDT, AVDT_CHAN_SIG);
118 
119     /* do not use security on the media channel */
120     BTM_SetSecurityLevel(TRUE, "", BTM_SEC_SERVICE_AVDTP_NOSEC, BTM_SEC_NONE,
121                          AVDT_PSM, BTM_SEC_PROTO_AVDT, AVDT_CHAN_MEDIA);
122     BTM_SetSecurityLevel(FALSE, "", BTM_SEC_SERVICE_AVDTP_NOSEC, BTM_SEC_NONE,
123                          AVDT_PSM, BTM_SEC_PROTO_AVDT, AVDT_CHAN_MEDIA);
124 
125 #if AVDT_REPORTING == TRUE
126     /* do not use security on the reporting channel */
127     BTM_SetSecurityLevel(TRUE, "", BTM_SEC_SERVICE_AVDTP_NOSEC, BTM_SEC_NONE,
128                          AVDT_PSM, BTM_SEC_PROTO_AVDT, AVDT_CHAN_REPORT);
129     BTM_SetSecurityLevel(FALSE, "", BTM_SEC_SERVICE_AVDTP_NOSEC, BTM_SEC_NONE,
130                          AVDT_PSM, BTM_SEC_PROTO_AVDT, AVDT_CHAN_REPORT);
131 #endif
132 
133     /* initialize AVDTP data structures */
134     avdt_scb_init();
135     avdt_ccb_init();
136     avdt_ad_init();
137 
138     /* copy registration struct */
139     memcpy(&avdt_cb.rcb, p_reg, sizeof(tAVDT_REG));
140     avdt_cb.p_conn_cback = p_cback;
141 }
142 
143 /*******************************************************************************
144 **
145 ** Function         AVDT_Deregister
146 **
147 ** Description      This function is called to deregister use AVDTP protocol.
148 **                  It is called when AVDTP is no longer being used by any
149 **                  application in the system.  Before this function can be
150 **                  called, all streams must be removed with AVDT_RemoveStream().
151 **
152 **
153 ** Returns          void
154 **
155 *******************************************************************************/
AVDT_Deregister(void)156 void AVDT_Deregister(void)
157 {
158     /* deregister PSM with L2CAP */
159     L2CA_Deregister(AVDT_PSM);
160 }
161 
162 /*******************************************************************************
163 **
164 ** Function         AVDT_SINK_Activate
165 **
166 ** Description      Activate SEP of A2DP Sink. In Use parameter is adjusted.
167 **                  In Use will be made false in case of activation. A2DP SRC
168 **                  will receive in_use as false and can open A2DP Sink
169 **                  connection
170 **
171 ** Returns          void.
172 **
173 *******************************************************************************/
AVDT_SINK_Activate(void)174 void AVDT_SINK_Activate(void)
175 {
176     tAVDT_SCB           *p_scb = &avdt_cb.scb[0];
177     int                 i;
178     AVDT_TRACE_DEBUG("AVDT_SINK_Activate");
179     /* for all allocated scbs */
180     for (i = 0; i < AVDT_NUM_SEPS; i++, p_scb++) {
181         if ((p_scb->allocated) && (p_scb->cs.tsep == AVDT_TSEP_SNK)) {
182             AVDT_TRACE_DEBUG("AVDT_SINK_Activate found scb");
183             p_scb->sink_activated = TRUE;
184             /* update in_use */
185             p_scb->in_use = FALSE;
186             break;
187         }
188     }
189 }
190 
191 /*******************************************************************************
192 **
193 ** Function         AVDT_SINK_Deactivate
194 **
195 ** Description      Deactivate SEP of A2DP Sink. In Use parameter is adjusted.
196 **                  In Use will be made TRUE in case of activation. A2DP SRC
197 **                  will receive in_use as true and will not open A2DP Sink
198 **                  connection
199 **
200 ** Returns          void.
201 **
202 *******************************************************************************/
AVDT_SINK_Deactivate(void)203 void AVDT_SINK_Deactivate(void)
204 {
205     tAVDT_SCB           *p_scb = &avdt_cb.scb[0];
206     int                 i;
207     AVDT_TRACE_DEBUG("AVDT_SINK_Deactivate");
208     /* for all allocated scbs */
209     for (i = 0; i < AVDT_NUM_SEPS; i++, p_scb++) {
210         if ((p_scb->allocated) && (p_scb->cs.tsep == AVDT_TSEP_SNK)) {
211             AVDT_TRACE_DEBUG("AVDT_SINK_Deactivate, found scb");
212             p_scb->sink_activated = FALSE;
213             /* update in_use */
214             p_scb->in_use = TRUE;
215             break;
216         }
217     }
218 }
219 
AVDT_AbortReq(UINT8 handle)220 void AVDT_AbortReq(UINT8 handle)
221 {
222     AVDT_TRACE_ERROR("%s\n", __func__);
223 
224     tAVDT_SCB *p_scb = avdt_scb_by_hdl(handle);
225     if (p_scb != NULL) {
226         avdt_scb_event(p_scb, AVDT_SCB_API_ABORT_REQ_EVT, NULL);
227     } else {
228         AVDT_TRACE_ERROR("%s Improper SCB, can not abort the stream\n", __func__);
229     }
230 }
231 
232 /*******************************************************************************
233 **
234 ** Function         AVDT_CreateStream
235 **
236 ** Description      Create a stream endpoint.  After a stream endpoint is
237 **                  created an application can initiate a connection between
238 **                  this endpoint and an endpoint on a peer device.  In
239 **                  addition, a peer device can discover, get the capabilities,
240 **                  and connect to this endpoint.
241 **
242 **
243 ** Returns          AVDT_SUCCESS if successful, otherwise error.
244 **
245 *******************************************************************************/
AVDT_CreateStream(UINT8 * p_handle,tAVDT_CS * p_cs)246 UINT16 AVDT_CreateStream(UINT8 *p_handle, tAVDT_CS *p_cs)
247 {
248     UINT16      result = AVDT_SUCCESS;
249     tAVDT_SCB   *p_scb;
250 
251     /* Verify parameters; if invalid, return failure */
252     if (((p_cs->cfg.psc_mask & (~AVDT_PSC)) != 0) || (p_cs->p_ctrl_cback == NULL)) {
253         result = AVDT_BAD_PARAMS;
254     }
255     /* Allocate scb; if no scbs, return failure */
256     else if ((p_scb = avdt_scb_alloc(p_cs)) == NULL) {
257         result = AVDT_NO_RESOURCES;
258     } else {
259         *p_handle = avdt_scb_to_hdl(p_scb);
260     }
261     return result;
262 }
263 
264 /*******************************************************************************
265 **
266 ** Function         AVDT_RemoveStream
267 **
268 ** Description      Remove a stream endpoint.  This function is called when
269 **                  the application is no longer using a stream endpoint.
270 **                  If this function is called when the endpoint is connected
271 **                  the connection is closed and then the stream endpoint
272 **                  is removed.
273 **
274 **
275 ** Returns          AVDT_SUCCESS if successful, otherwise error.
276 **
277 *******************************************************************************/
AVDT_RemoveStream(UINT8 handle)278 UINT16 AVDT_RemoveStream(UINT8 handle)
279 {
280     UINT16      result = AVDT_SUCCESS;
281     tAVDT_SCB   *p_scb;
282 
283     /* look up scb */
284     if ((p_scb = avdt_scb_by_hdl(handle)) == NULL) {
285         result = AVDT_BAD_HANDLE;
286     } else {
287         /* send remove event to scb */
288         avdt_scb_event(p_scb, AVDT_SCB_API_REMOVE_EVT, NULL);
289     }
290     return result;
291 }
292 
293 /*******************************************************************************
294 **
295 ** Function         AVDT_DiscoverReq
296 **
297 ** Description      This function initiates a connection to the AVDTP service
298 **                  on the peer device, if not already present, and discovers
299 **                  the stream endpoints on the peer device.  (Please note
300 **                  that AVDTP discovery is unrelated to SDP discovery).
301 **                  This function can be called at any time regardless of whether
302 **                  there is an AVDTP connection to the peer device.
303 **
304 **                  When discovery is complete, an AVDT_DISCOVER_CFM_EVT
305 **                  is sent to the application via its callback function.
306 **                  The application must not call AVDT_GetCapReq() or
307 **                  AVDT_DiscoverReq() again to the same device until
308 **                  discovery is complete.
309 **
310 **                  The memory addressed by sep_info is allocated by the
311 **                  application.  This memory is written to by AVDTP as part
312 **                  of the discovery procedure.  This memory must remain
313 **                  accessible until the application receives the
314 **                  AVDT_DISCOVER_CFM_EVT.
315 **
316 ** Returns          AVDT_SUCCESS if successful, otherwise error.
317 **
318 *******************************************************************************/
AVDT_DiscoverReq(BD_ADDR bd_addr,tAVDT_SEP_INFO * p_sep_info,UINT8 max_seps,tAVDT_CTRL_CBACK * p_cback)319 UINT16 AVDT_DiscoverReq(BD_ADDR bd_addr, tAVDT_SEP_INFO *p_sep_info,
320                         UINT8 max_seps, tAVDT_CTRL_CBACK *p_cback)
321 {
322     tAVDT_CCB       *p_ccb;
323     UINT16          result = AVDT_SUCCESS;
324     tAVDT_CCB_EVT   evt;
325 
326     /* find channel control block for this bd addr; if none, allocate one */
327     if ((p_ccb = avdt_ccb_by_bd(bd_addr)) == NULL) {
328         if ((p_ccb = avdt_ccb_alloc(bd_addr)) == NULL) {
329             /* could not allocate channel control block */
330             result = AVDT_NO_RESOURCES;
331         }
332     }
333 
334     if (result == AVDT_SUCCESS) {
335         /* make sure no discovery or get capabilities req already in progress */
336         if (p_ccb->proc_busy) {
337             result = AVDT_BUSY;
338         }
339         /* send event to ccb */
340         else {
341             evt.discover.p_sep_info = p_sep_info;
342             evt.discover.num_seps = max_seps;
343             evt.discover.p_cback = p_cback;
344             avdt_ccb_event(p_ccb, AVDT_CCB_API_DISCOVER_REQ_EVT, &evt);
345         }
346     }
347     return result;
348 }
349 
350 /*******************************************************************************
351 **
352 ** Function         avdt_get_cap_req
353 **
354 ** Description      internal function to serve both AVDT_GetCapReq and
355 **                  AVDT_GetAllCapReq
356 **
357 ** Returns          AVDT_SUCCESS if successful, otherwise error.
358 **
359 *******************************************************************************/
avdt_get_cap_req(BD_ADDR bd_addr,tAVDT_CCB_API_GETCAP * p_evt)360 static UINT16 avdt_get_cap_req(BD_ADDR bd_addr, tAVDT_CCB_API_GETCAP *p_evt)
361 {
362     tAVDT_CCB       *p_ccb = NULL;
363     UINT16          result = AVDT_SUCCESS;
364 
365     /* verify SEID */
366     if ((p_evt->single.seid < AVDT_SEID_MIN) || (p_evt->single.seid > AVDT_SEID_MAX)) {
367         AVDT_TRACE_ERROR("seid: %d\n", p_evt->single.seid);
368         result = AVDT_BAD_PARAMS;
369     }
370     /* find channel control block for this bd addr; if none, allocate one */
371     else if ((p_ccb = avdt_ccb_by_bd(bd_addr)) == NULL) {
372         if ((p_ccb = avdt_ccb_alloc(bd_addr)) == NULL) {
373             /* could not allocate channel control block */
374             result = AVDT_NO_RESOURCES;
375         }
376     }
377 
378     if (result == AVDT_SUCCESS) {
379         /* make sure no discovery or get capabilities req already in progress */
380         if (p_ccb->proc_busy) {
381             result = AVDT_BUSY;
382         }
383         /* send event to ccb */
384         else {
385             avdt_ccb_event(p_ccb, AVDT_CCB_API_GETCAP_REQ_EVT, (tAVDT_CCB_EVT *)p_evt);
386         }
387     }
388     return result;
389 }
390 
391 /*******************************************************************************
392 **
393 ** Function         AVDT_GetCapReq
394 **
395 ** Description      This function initiates a connection to the AVDTP service
396 **                  on the peer device, if not already present, and gets the
397 **                  capabilities of a stream endpoint on the peer device.
398 **                  This function can be called at any time regardless of
399 **                  whether there is an AVDTP connection to the peer device.
400 **
401 **                  When the procedure is complete, an AVDT_GETCAP_CFM_EVT is
402 **                  sent to the application via its callback function.  The
403 **                  application must not call AVDT_GetCapReq() or
404 **                  AVDT_DiscoverReq() again until the procedure is complete.
405 **
406 **                  The memory pointed to by p_cfg is allocated by the
407 **                  application.  This memory is written to by AVDTP as part
408 **                  of the get capabilities procedure.  This memory must
409 **                  remain accessible until the application receives
410 **                  the AVDT_GETCAP_CFM_EVT.
411 **
412 ** Returns          AVDT_SUCCESS if successful, otherwise error.
413 **
414 *******************************************************************************/
AVDT_GetCapReq(BD_ADDR bd_addr,UINT8 seid,tAVDT_CFG * p_cfg,tAVDT_CTRL_CBACK * p_cback)415 UINT16 AVDT_GetCapReq(BD_ADDR bd_addr, UINT8 seid, tAVDT_CFG *p_cfg, tAVDT_CTRL_CBACK *p_cback)
416 {
417     tAVDT_CCB_API_GETCAP    getcap;
418 
419     getcap.single.seid = seid;
420     getcap.single.sig_id = AVDT_SIG_GETCAP;
421     getcap.p_cfg = p_cfg;
422     getcap.p_cback = p_cback;
423     return avdt_get_cap_req (bd_addr, &getcap);
424 }
425 
426 /*******************************************************************************
427 **
428 ** Function         AVDT_GetAllCapReq
429 **
430 ** Description      This function initiates a connection to the AVDTP service
431 **                  on the peer device, if not already present, and gets the
432 **                  capabilities of a stream endpoint on the peer device.
433 **                  This function can be called at any time regardless of
434 **                  whether there is an AVDTP connection to the peer device.
435 **
436 **                  When the procedure is complete, an AVDT_GETCAP_CFM_EVT is
437 **                  sent to the application via its callback function.  The
438 **                  application must not call AVDT_GetCapReq() or
439 **                  AVDT_DiscoverReq() again until the procedure is complete.
440 **
441 **                  The memory pointed to by p_cfg is allocated by the
442 **                  application.  This memory is written to by AVDTP as part
443 **                  of the get capabilities procedure.  This memory must
444 **                  remain accessible until the application receives
445 **                  the AVDT_GETCAP_CFM_EVT.
446 **
447 ** Returns          AVDT_SUCCESS if successful, otherwise error.
448 **
449 *******************************************************************************/
AVDT_GetAllCapReq(BD_ADDR bd_addr,UINT8 seid,tAVDT_CFG * p_cfg,tAVDT_CTRL_CBACK * p_cback)450 UINT16 AVDT_GetAllCapReq(BD_ADDR bd_addr, UINT8 seid, tAVDT_CFG *p_cfg, tAVDT_CTRL_CBACK *p_cback)
451 {
452     tAVDT_CCB_API_GETCAP    getcap;
453 
454     getcap.single.seid = seid;
455     getcap.single.sig_id = AVDT_SIG_GET_ALLCAP;
456     getcap.p_cfg = p_cfg;
457     getcap.p_cback = p_cback;
458     return avdt_get_cap_req (bd_addr, &getcap);
459 }
460 
461 /*******************************************************************************
462 **
463 ** Function         AVDT_DelayReport
464 **
465 ** Description      This functions sends a Delay Report to the peer device
466 **                  that is associated with a particular SEID.
467 **                  This function is called by SNK device.
468 **
469 ** Returns          AVDT_SUCCESS if successful, otherwise error.
470 **
471 *******************************************************************************/
AVDT_DelayReport(UINT8 handle,UINT8 seid,UINT16 delay)472 UINT16 AVDT_DelayReport(UINT8 handle, UINT8 seid, UINT16 delay)
473 {
474     tAVDT_SCB       *p_scb;
475     UINT16          result = AVDT_SUCCESS;
476     tAVDT_SCB_EVT   evt;
477 
478     /* map handle to scb */
479     if ((p_scb = avdt_scb_by_hdl(handle)) == NULL) {
480         result = AVDT_BAD_HANDLE;
481     } else
482         /* send event to scb */
483     {
484         evt.apidelay.hdr.seid   = seid;
485         evt.apidelay.delay      = delay;
486         avdt_scb_event(p_scb, AVDT_SCB_API_DELAY_RPT_REQ_EVT, &evt);
487     }
488 
489     return result;
490 }
491 
492 /*******************************************************************************
493 **
494 ** Function         AVDT_OpenReq
495 **
496 ** Description      This function initiates a connection to the AVDTP service
497 **                  on the peer device, if not already present, and connects
498 **                  to a stream endpoint on a peer device.  When the connection
499 **                  is completed, an AVDT_OPEN_CFM_EVT is sent to the
500 **                  application via the control callback function for this handle.
501 **
502 ** Returns          AVDT_SUCCESS if successful, otherwise error.
503 **
504 *******************************************************************************/
AVDT_OpenReq(UINT8 handle,BD_ADDR bd_addr,UINT8 seid,tAVDT_CFG * p_cfg)505 UINT16 AVDT_OpenReq(UINT8 handle, BD_ADDR bd_addr, UINT8 seid, tAVDT_CFG *p_cfg)
506 {
507     tAVDT_CCB       *p_ccb = NULL;
508     tAVDT_SCB       *p_scb = NULL;
509     UINT16          result = AVDT_SUCCESS;
510     tAVDT_SCB_EVT   evt;
511 
512     /* verify SEID */
513     if ((seid < AVDT_SEID_MIN) || (seid > AVDT_SEID_MAX)) {
514         result = AVDT_BAD_PARAMS;
515     }
516     /* map handle to scb */
517     else if ((p_scb = avdt_scb_by_hdl(handle)) == NULL) {
518         result = AVDT_BAD_HANDLE;
519     }
520     /* find channel control block for this bd addr; if none, allocate one */
521     else if ((p_ccb = avdt_ccb_by_bd(bd_addr)) == NULL) {
522         if ((p_ccb = avdt_ccb_alloc(bd_addr)) == NULL) {
523             /* could not allocate channel control block */
524             result = AVDT_NO_RESOURCES;
525         }
526     }
527 
528     /* send event to scb */
529     if (result == AVDT_SUCCESS) {
530         evt.msg.config_cmd.hdr.seid = seid;
531         evt.msg.config_cmd.hdr.ccb_idx = avdt_ccb_to_idx(p_ccb);
532         evt.msg.config_cmd.int_seid = handle;
533         evt.msg.config_cmd.p_cfg = p_cfg;
534         avdt_scb_event(p_scb, AVDT_SCB_API_SETCONFIG_REQ_EVT, &evt);
535     }
536     return result;
537 }
538 
539 /*******************************************************************************
540 **
541 ** Function         AVDT_ConfigRsp
542 **
543 ** Description      Respond to a configure request from the peer device.  This
544 **                  function must be called if the application receives an
545 **                  AVDT_CONFIG_IND_EVT through its control callback.
546 **
547 **
548 ** Returns          AVDT_SUCCESS if successful, otherwise error.
549 **
550 *******************************************************************************/
AVDT_ConfigRsp(UINT8 handle,UINT8 label,UINT8 error_code,UINT8 category)551 UINT16 AVDT_ConfigRsp(UINT8 handle, UINT8 label, UINT8 error_code, UINT8 category)
552 {
553     tAVDT_SCB       *p_scb;
554     tAVDT_SCB_EVT   evt;
555     UINT16          result = AVDT_SUCCESS;
556     UINT8           event_code;
557 
558     /* map handle to scb */
559     if ((p_scb = avdt_scb_by_hdl(handle)) == NULL) {
560         result = AVDT_BAD_HANDLE;
561     }
562     /* handle special case when this function is called but peer has not send
563     ** a configuration cmd; ignore and return error result
564     */
565     else if (!p_scb->in_use) {
566         result = AVDT_BAD_HANDLE;
567     }
568     /* send event to scb */
569     else {
570         evt.msg.hdr.err_code = error_code;
571         evt.msg.hdr.err_param = category;
572         evt.msg.hdr.label = label;
573         if (error_code == 0) {
574             event_code = AVDT_SCB_API_SETCONFIG_RSP_EVT;
575         } else {
576             event_code = AVDT_SCB_API_SETCONFIG_REJ_EVT;
577         }
578         avdt_scb_event(p_scb, event_code, &evt);
579     }
580 
581     return result;
582 }
583 
584 /*******************************************************************************
585 **
586 ** Function         AVDT_StartReq
587 **
588 ** Description      Start one or more stream endpoints.  This initiates the
589 **                  transfer of media packets for the streams.  All stream
590 **                  endpoints must previously be opened.  When the streams
591 **                  are started, an AVDT_START_CFM_EVT is sent to the
592 **                  application via the control callback function for each stream.
593 **
594 **
595 ** Returns          AVDT_SUCCESS if successful, otherwise error.
596 **
597 *******************************************************************************/
AVDT_StartReq(UINT8 * p_handles,UINT8 num_handles)598 UINT16 AVDT_StartReq(UINT8 *p_handles, UINT8 num_handles)
599 {
600     tAVDT_SCB       *p_scb = NULL;
601     tAVDT_CCB_EVT   evt;
602     UINT16          result = AVDT_SUCCESS;
603     int             i;
604 
605     if ((num_handles == 0) || (num_handles > AVDT_NUM_SEPS)) {
606         result = AVDT_BAD_PARAMS;
607     } else {
608         /* verify handles */
609         for (i = 0; i < num_handles; i++) {
610             if ((p_scb = avdt_scb_by_hdl(p_handles[i])) == NULL) {
611                 result = AVDT_BAD_HANDLE;
612                 break;
613             }
614         }
615     }
616 
617     if (result == AVDT_SUCCESS) {
618         if (p_scb->p_ccb == NULL) {
619             result = AVDT_BAD_HANDLE;
620         } else {
621             /* send event to ccb */
622             memcpy(evt.msg.multi.seid_list, p_handles, num_handles);
623             evt.msg.multi.num_seps = num_handles;
624             avdt_ccb_event(p_scb->p_ccb, AVDT_CCB_API_START_REQ_EVT, &evt);
625         }
626     }
627     return result;
628 }
629 
630 /*******************************************************************************
631 **
632 ** Function         AVDT_SuspendReq
633 **
634 ** Description      Suspend one or more stream endpoints. This suspends the
635 **                  transfer of media packets for the streams.  All stream
636 **                  endpoints must previously be open and started.  When the
637 **                  streams are suspended, an AVDT_SUSPEND_CFM_EVT is sent to
638 **                  the application via the control callback function for
639 **                  each stream.
640 **
641 **
642 ** Returns          AVDT_SUCCESS if successful, otherwise error.
643 **
644 *******************************************************************************/
AVDT_SuspendReq(UINT8 * p_handles,UINT8 num_handles)645 UINT16 AVDT_SuspendReq(UINT8 *p_handles, UINT8 num_handles)
646 {
647     tAVDT_SCB       *p_scb = NULL;
648     tAVDT_CCB_EVT   evt;
649     UINT16          result = AVDT_SUCCESS;
650     int             i;
651 
652     if ((num_handles == 0) || (num_handles > AVDT_NUM_SEPS)) {
653         result = AVDT_BAD_PARAMS;
654     } else {
655         /* verify handles */
656         for (i = 0; i < num_handles; i++) {
657             if ((p_scb = avdt_scb_by_hdl(p_handles[i])) == NULL) {
658                 result = AVDT_BAD_HANDLE;
659                 break;
660             }
661         }
662     }
663 
664     if (result == AVDT_SUCCESS) {
665         if (p_scb->p_ccb == NULL) {
666             result = AVDT_BAD_HANDLE;
667         } else {
668             /* send event to ccb */
669             memcpy(evt.msg.multi.seid_list, p_handles, num_handles);
670             evt.msg.multi.num_seps = num_handles;
671             avdt_ccb_event(p_scb->p_ccb, AVDT_CCB_API_SUSPEND_REQ_EVT, &evt);
672         }
673     }
674 
675     return result;
676 }
677 
678 /*******************************************************************************
679 **
680 ** Function         AVDT_CloseReq
681 **
682 ** Description      Close a stream endpoint.  This stops the transfer of media
683 **                  packets and closes the transport channel associated with
684 **                  this stream endpoint.  When the stream is closed, an
685 **                  AVDT_CLOSE_CFM_EVT is sent to the application via the
686 **                  control callback function for this handle.
687 **
688 **
689 ** Returns          AVDT_SUCCESS if successful, otherwise error.
690 **
691 *******************************************************************************/
AVDT_CloseReq(UINT8 handle)692 UINT16 AVDT_CloseReq(UINT8 handle)
693 {
694     tAVDT_SCB       *p_scb;
695     UINT16          result = AVDT_SUCCESS;
696 
697     /* map handle to scb */
698     if ((p_scb = avdt_scb_by_hdl(handle)) == NULL) {
699         result = AVDT_BAD_HANDLE;
700     } else
701         /* send event to scb */
702     {
703         avdt_scb_event(p_scb, AVDT_SCB_API_CLOSE_REQ_EVT, NULL);
704     }
705 
706     return result;
707 }
708 
709 /*******************************************************************************
710 **
711 ** Function         AVDT_ReconfigReq
712 **
713 ** Description      Reconfigure a stream endpoint.  This allows the application
714 **                  to change the codec or content protection capabilities of
715 **                  a stream endpoint after it has been opened.  This function
716 **                  can only be called if the stream is opened but not started
717 **                  or if the stream has been suspended.  When the procedure
718 **                  is completed, an AVDT_RECONFIG_CFM_EVT is sent to the
719 **                  application via the control callback function for this handle.
720 **
721 **
722 ** Returns          AVDT_SUCCESS if successful, otherwise error.
723 **
724 *******************************************************************************/
AVDT_ReconfigReq(UINT8 handle,tAVDT_CFG * p_cfg)725 UINT16 AVDT_ReconfigReq(UINT8 handle, tAVDT_CFG *p_cfg)
726 {
727     tAVDT_SCB       *p_scb;
728     UINT16          result = AVDT_SUCCESS;
729     tAVDT_SCB_EVT   evt;
730 
731     /* map handle to scb */
732     if ((p_scb = avdt_scb_by_hdl(handle)) == NULL) {
733         result = AVDT_BAD_HANDLE;
734     }
735     /* send event to scb */
736     else {
737         /* force psc_mask to zero */
738         p_cfg->psc_mask = 0;
739 
740         evt.msg.reconfig_cmd.p_cfg = p_cfg;
741         avdt_scb_event(p_scb, AVDT_SCB_API_RECONFIG_REQ_EVT, &evt);
742     }
743     return result;
744 }
745 
746 /*******************************************************************************
747 **
748 ** Function         AVDT_ReconfigRsp
749 **
750 ** Description      Respond to a reconfigure request from the peer device.
751 **                  This function must be called if the application receives
752 **                  an AVDT_RECONFIG_IND_EVT through its control callback.
753 **
754 **
755 ** Returns          AVDT_SUCCESS if successful, otherwise error.
756 **
757 *******************************************************************************/
AVDT_ReconfigRsp(UINT8 handle,UINT8 label,UINT8 error_code,UINT8 category)758 UINT16 AVDT_ReconfigRsp(UINT8 handle, UINT8 label, UINT8 error_code, UINT8 category)
759 {
760     tAVDT_SCB       *p_scb;
761     tAVDT_SCB_EVT   evt;
762     UINT16          result = AVDT_SUCCESS;
763 
764     /* map handle to scb */
765     if ((p_scb = avdt_scb_by_hdl(handle)) == NULL) {
766         result = AVDT_BAD_HANDLE;
767     }
768     /* send event to scb */
769     else {
770         evt.msg.hdr.err_code = error_code;
771         evt.msg.hdr.err_param = category;
772         evt.msg.hdr.label = label;
773         avdt_scb_event(p_scb, AVDT_SCB_API_RECONFIG_RSP_EVT, &evt);
774     }
775 
776     return result;
777 }
778 
779 /*******************************************************************************
780 **
781 ** Function         AVDT_SecurityReq
782 **
783 ** Description      Send a security request to the peer device.  When the
784 **                  security procedure is completed, an AVDT_SECURITY_CFM_EVT
785 **                  is sent to the application via the control callback function
786 **                  for this handle.  (Please note that AVDTP security procedures
787 **                  are unrelated to Bluetooth link level security.)
788 **
789 **
790 ** Returns          AVDT_SUCCESS if successful, otherwise error.
791 **
792 *******************************************************************************/
AVDT_SecurityReq(UINT8 handle,UINT8 * p_data,UINT16 len)793 UINT16 AVDT_SecurityReq(UINT8 handle, UINT8 *p_data, UINT16 len)
794 {
795     tAVDT_SCB       *p_scb;
796     UINT16          result = AVDT_SUCCESS;
797     tAVDT_SCB_EVT   evt;
798 
799     /* map handle to scb */
800     if ((p_scb = avdt_scb_by_hdl(handle)) == NULL) {
801         result = AVDT_BAD_HANDLE;
802     }
803     /* send event to scb */
804     else {
805         evt.msg.security_rsp.p_data = p_data;
806         evt.msg.security_rsp.len = len;
807         avdt_scb_event(p_scb, AVDT_SCB_API_SECURITY_REQ_EVT, &evt);
808     }
809     return result;
810 }
811 
812 /*******************************************************************************
813 **
814 ** Function         AVDT_SecurityRsp
815 **
816 ** Description      Respond to a security request from the peer device.
817 **                  This function must be called if the application receives
818 **                  an AVDT_SECURITY_IND_EVT through its control callback.
819 **                  (Please note that AVDTP security procedures are unrelated
820 **                  to Bluetooth link level security.)
821 **
822 **
823 ** Returns          AVDT_SUCCESS if successful, otherwise error.
824 **
825 *******************************************************************************/
AVDT_SecurityRsp(UINT8 handle,UINT8 label,UINT8 error_code,UINT8 * p_data,UINT16 len)826 UINT16 AVDT_SecurityRsp(UINT8 handle, UINT8 label, UINT8 error_code,
827                         UINT8 *p_data, UINT16 len)
828 {
829     tAVDT_SCB       *p_scb;
830     UINT16          result = AVDT_SUCCESS;
831     tAVDT_SCB_EVT   evt;
832 
833     /* map handle to scb */
834     if ((p_scb = avdt_scb_by_hdl(handle)) == NULL) {
835         result = AVDT_BAD_HANDLE;
836     }
837     /* send event to scb */
838     else {
839         evt.msg.security_rsp.hdr.err_code = error_code;
840         evt.msg.security_rsp.hdr.label = label;
841         evt.msg.security_rsp.p_data = p_data;
842         evt.msg.security_rsp.len = len;
843         avdt_scb_event(p_scb, AVDT_SCB_API_SECURITY_RSP_EVT, &evt);
844     }
845     return result;
846 }
847 
848 /*******************************************************************************
849 **
850 ** Function         AVDT_WriteReqOpt
851 **
852 ** Description      Send a media packet to the peer device.  The stream must
853 **                  be started before this function is called.  Also, this
854 **                  function can only be called if the stream is a SRC.
855 **
856 **                  When AVDTP has sent the media packet and is ready for the
857 **                  next packet, an AVDT_WRITE_CFM_EVT is sent to the
858 **                  application via the control callback.  The application must
859 **                  wait for the AVDT_WRITE_CFM_EVT before it makes the next
860 **                  call to AVDT_WriteReq().  If the applications calls
861 **                  AVDT_WriteReq() before it receives the event the packet
862 **                  will not be sent.  The application may make its first call
863 **                  to AVDT_WriteReq() after it receives an AVDT_START_CFM_EVT
864 **                  or AVDT_START_IND_EVT.
865 **
866 **                  The application passes the packet using the BT_HDR structure.
867 **                  This structure is described in section 2.1.  The offset
868 **                  field must be equal to or greater than AVDT_MEDIA_OFFSET
869 **                  (if NO_RTP is specified, L2CAP_MIN_OFFSET can be used).
870 **                  This allows enough space in the buffer for the L2CAP and
871 **                  AVDTP headers.
872 **
873 **                  The memory pointed to by p_pkt must be a GKI buffer
874 **                  allocated by the application.  This buffer will be freed
875 **                  by the protocol stack; the application must not free
876 **                  this buffer.
877 **
878 **                  The opt parameter allows passing specific options like:
879 **                  - NO_RTP : do not add the RTP header to buffer
880 **
881 ** Returns          AVDT_SUCCESS if successful, otherwise error.
882 **
883 *******************************************************************************/
AVDT_WriteReqOpt(UINT8 handle,BT_HDR * p_pkt,UINT32 time_stamp,UINT8 m_pt,tAVDT_DATA_OPT_MASK opt)884 UINT16 AVDT_WriteReqOpt(UINT8 handle, BT_HDR *p_pkt, UINT32 time_stamp, UINT8 m_pt, tAVDT_DATA_OPT_MASK opt)
885 {
886     tAVDT_SCB       *p_scb;
887     tAVDT_SCB_EVT   evt;
888     UINT16          result = AVDT_SUCCESS;
889 
890     /* map handle to scb */
891     if ((p_scb = avdt_scb_by_hdl(handle)) == NULL) {
892         result = AVDT_BAD_HANDLE;
893     } else {
894         evt.apiwrite.p_buf = p_pkt;
895         evt.apiwrite.time_stamp = time_stamp;
896         evt.apiwrite.m_pt = m_pt;
897         evt.apiwrite.opt = opt;
898         avdt_scb_event(p_scb, AVDT_SCB_API_WRITE_REQ_EVT, &evt);
899     }
900 
901     return result;
902 }
903 
904 /*******************************************************************************
905 **
906 ** Function         AVDT_WriteReq
907 **
908 ** Description      Send a media packet to the peer device.  The stream must
909 **                  be started before this function is called.  Also, this
910 **                  function can only be called if the stream is a SRC.
911 **
912 **                  When AVDTP has sent the media packet and is ready for the
913 **                  next packet, an AVDT_WRITE_CFM_EVT is sent to the
914 **                  application via the control callback.  The application must
915 **                  wait for the AVDT_WRITE_CFM_EVT before it makes the next
916 **                  call to AVDT_WriteReq().  If the applications calls
917 **                  AVDT_WriteReq() before it receives the event the packet
918 **                  will not be sent.  The application may make its first call
919 **                  to AVDT_WriteReq() after it receives an AVDT_START_CFM_EVT
920 **                  or AVDT_START_IND_EVT.
921 **
922 **                  The application passes the packet using the BT_HDR structure.
923 **                  This structure is described in section 2.1.  The offset
924 **                  field must be equal to or greater than AVDT_MEDIA_OFFSET.
925 **                  This allows enough space in the buffer for the L2CAP and
926 **                  AVDTP headers.
927 **
928 **                  The memory pointed to by p_pkt must be a GKI buffer
929 **                  allocated by the application.  This buffer will be freed
930 **                  by the protocol stack; the application must not free
931 **                  this buffer.
932 **
933 **
934 ** Returns          AVDT_SUCCESS if successful, otherwise error.
935 **
936 *******************************************************************************/
AVDT_WriteReq(UINT8 handle,BT_HDR * p_pkt,UINT32 time_stamp,UINT8 m_pt)937 UINT16 AVDT_WriteReq(UINT8 handle, BT_HDR *p_pkt, UINT32 time_stamp, UINT8 m_pt)
938 {
939     return AVDT_WriteReqOpt(handle, p_pkt, time_stamp, m_pt, AVDT_DATA_OPT_NONE);
940 }
941 
942 /*******************************************************************************
943 **
944 ** Function         AVDT_ConnectReq
945 **
946 ** Description      This function initiates an AVDTP signaling connection
947 **                  to the peer device.  When the connection is completed, an
948 **                  AVDT_CONNECT_IND_EVT is sent to the application via its
949 **                  control callback function.  If the connection attempt fails
950 **                  an AVDT_DISCONNECT_IND_EVT is sent.  The security mask
951 **                  parameter overrides the outgoing security mask set in
952 **                  AVDT_Register().
953 **
954 ** Returns          AVDT_SUCCESS if successful, otherwise error.
955 **
956 *******************************************************************************/
AVDT_ConnectReq(BD_ADDR bd_addr,UINT8 sec_mask,tAVDT_CTRL_CBACK * p_cback)957 UINT16 AVDT_ConnectReq(BD_ADDR bd_addr, UINT8 sec_mask, tAVDT_CTRL_CBACK *p_cback)
958 {
959     tAVDT_CCB       *p_ccb = NULL;
960     UINT16          result = AVDT_SUCCESS;
961     tAVDT_CCB_EVT   evt;
962 
963     /* find channel control block for this bd addr; if none, allocate one */
964     if ((p_ccb = avdt_ccb_by_bd(bd_addr)) == NULL) {
965         if ((p_ccb = avdt_ccb_alloc(bd_addr)) == NULL) {
966             /* could not allocate channel control block */
967             result = AVDT_NO_RESOURCES;
968         }
969     } else if (p_ccb->ll_opened == FALSE) {
970         AVDT_TRACE_WARNING("AVDT_ConnectReq: CCB LL is in the middle of opening");
971 
972         /* ccb was already allocated for the incoming signalling. */
973         result = AVDT_BUSY;
974     }
975 
976     if (result == AVDT_SUCCESS) {
977         /* send event to ccb */
978         evt.connect.p_cback = p_cback;
979         evt.connect.sec_mask = sec_mask;
980         avdt_ccb_event(p_ccb, AVDT_CCB_API_CONNECT_REQ_EVT, &evt);
981     }
982     return result;
983 }
984 
985 /*******************************************************************************
986 **
987 ** Function         AVDT_DisconnectReq
988 **
989 ** Description      This function disconnect an AVDTP signaling connection
990 **                  to the peer device.  When disconnected an
991 **                  AVDT_DISCONNECT_IND_EVT is sent to the application via its
992 **                  control callback function.
993 **
994 ** Returns          AVDT_SUCCESS if successful, otherwise error.
995 **
996 *******************************************************************************/
AVDT_DisconnectReq(BD_ADDR bd_addr,tAVDT_CTRL_CBACK * p_cback)997 UINT16 AVDT_DisconnectReq(BD_ADDR bd_addr, tAVDT_CTRL_CBACK *p_cback)
998 {
999     tAVDT_CCB       *p_ccb = NULL;
1000     UINT16          result = AVDT_SUCCESS;
1001     tAVDT_CCB_EVT   evt;
1002 
1003     /* find channel control block for this bd addr; if none, error */
1004     if ((p_ccb = avdt_ccb_by_bd(bd_addr)) == NULL) {
1005         result = AVDT_BAD_PARAMS;
1006     }
1007 
1008     if (result == AVDT_SUCCESS) {
1009         /* send event to ccb */
1010         evt.disconnect.p_cback = p_cback;
1011         avdt_ccb_event(p_ccb, AVDT_CCB_API_DISCONNECT_REQ_EVT, &evt);
1012     }
1013     return result;
1014 }
1015 
1016 /*******************************************************************************
1017 **
1018 ** Function         AVDT_GetL2CapChannel
1019 **
1020 ** Description      Get the L2CAP CID used by the handle.
1021 **
1022 ** Returns          CID if successful, otherwise 0.
1023 **
1024 *******************************************************************************/
AVDT_GetL2CapChannel(UINT8 handle)1025 UINT16 AVDT_GetL2CapChannel(UINT8 handle)
1026 {
1027     tAVDT_SCB       *p_scb;
1028     tAVDT_CCB       *p_ccb;
1029     UINT8           tcid;
1030     UINT16          lcid = 0;
1031 
1032     /* map handle to scb */
1033     if (((p_scb = avdt_scb_by_hdl(handle)) != NULL)
1034             && ((p_ccb = p_scb->p_ccb) != NULL)) {
1035         /* get tcid from type, scb */
1036         tcid = avdt_ad_type_to_tcid(AVDT_CHAN_MEDIA, p_scb);
1037 
1038         lcid = avdt_cb.ad.rt_tbl[avdt_ccb_to_idx(p_ccb)][tcid].lcid;
1039     }
1040 
1041     return (lcid);
1042 }
1043 
1044 /*******************************************************************************
1045 **
1046 ** Function         AVDT_GetSignalChannel
1047 **
1048 ** Description      Get the L2CAP CID used by the signal channel of the given handle.
1049 **
1050 ** Returns          CID if successful, otherwise 0.
1051 **
1052 *******************************************************************************/
AVDT_GetSignalChannel(UINT8 handle,BD_ADDR bd_addr)1053 UINT16 AVDT_GetSignalChannel(UINT8 handle, BD_ADDR bd_addr)
1054 {
1055     tAVDT_SCB       *p_scb;
1056     tAVDT_CCB       *p_ccb;
1057     UINT8           tcid = 0; /* tcid is always 0 for signal channel */
1058     UINT16          lcid = 0;
1059 
1060     /* map handle to scb */
1061     if (((p_scb = avdt_scb_by_hdl(handle)) != NULL)
1062             && ((p_ccb = p_scb->p_ccb) != NULL)) {
1063         lcid = avdt_cb.ad.rt_tbl[avdt_ccb_to_idx(p_ccb)][tcid].lcid;
1064     } else if ((p_ccb = avdt_ccb_by_bd(bd_addr)) != NULL) {
1065         lcid = avdt_cb.ad.rt_tbl[avdt_ccb_to_idx(p_ccb)][tcid].lcid;
1066     }
1067 
1068     return (lcid);
1069 }
1070 
1071 
1072 
1073 #if AVDT_MULTIPLEXING == TRUE
1074 /*******************************************************************************
1075 **
1076 ** Function         AVDT_SetMediaBuf
1077 **
1078 ** Description      Assigns buffer for media packets or forbids using of assigned
1079 **                  buffer if argument p_buf is NULL. This function can only
1080 **                  be called if the stream is a SNK.
1081 **
1082 **                  AVDTP uses this buffer to reassemble fragmented media packets.
1083 **                  When AVDTP receives a complete media packet, it calls the
1084 **                  p_media_cback assigned by AVDT_CreateStream().
1085 **                  This function can be called during callback to assign a
1086 **                  different buffer for next media packet or can leave the current
1087 **                  buffer for next packet.
1088 **
1089 ** Returns          AVDT_SUCCESS if successful, otherwise error.
1090 **
1091 *******************************************************************************/
AVDT_SetMediaBuf(UINT8 handle,UINT8 * p_buf,UINT32 buf_len)1092 extern UINT16 AVDT_SetMediaBuf(UINT8 handle, UINT8 *p_buf, UINT32 buf_len)
1093 {
1094     tAVDT_SCB       *p_scb;
1095     UINT16          result = AVDT_SUCCESS;
1096 
1097     /* map handle to scb */
1098     if ((p_scb = avdt_scb_by_hdl(handle)) == NULL) {
1099         result = AVDT_BAD_HANDLE;
1100     } else {
1101         if (p_buf && p_scb->cs.p_media_cback == NULL) {
1102             result = AVDT_NO_RESOURCES;
1103         } else {
1104             p_scb->p_media_buf = p_buf;
1105             p_scb->media_buf_len = buf_len;
1106         }
1107     }
1108 
1109     return result;
1110 }
1111 #endif
1112 
1113 #if AVDT_REPORTING == TRUE
1114 /*******************************************************************************
1115 **
1116 ** Function         AVDT_SendReport
1117 **
1118 ** Description
1119 **
1120 **
1121 **
1122 ** Returns
1123 **
1124 *******************************************************************************/
AVDT_SendReport(UINT8 handle,AVDT_REPORT_TYPE type,tAVDT_REPORT_DATA * p_data)1125 UINT16 AVDT_SendReport(UINT8 handle, AVDT_REPORT_TYPE type,
1126                        tAVDT_REPORT_DATA *p_data)
1127 {
1128     tAVDT_SCB       *p_scb;
1129     UINT16          result = AVDT_BAD_PARAMS;
1130     BT_HDR          *p_pkt;
1131     tAVDT_TC_TBL    *p_tbl;
1132     UINT8           *p, *plen, *pm1, *p_end;
1133 #if AVDT_MULTIPLEXING == TRUE
1134     UINT8           *p_al = NULL, u;
1135 #endif
1136     UINT32  ssrc;
1137     UINT16  len;
1138 
1139     /* map handle to scb && verify parameters */
1140     if (((p_scb = avdt_scb_by_hdl(handle)) != NULL)
1141             && (p_scb->p_ccb != NULL)
1142             && (((type == AVDT_RTCP_PT_SR) && (p_scb->cs.tsep == AVDT_TSEP_SRC)) ||
1143                 ((type == AVDT_RTCP_PT_RR) && (p_scb->cs.tsep == AVDT_TSEP_SNK)) ||
1144                 (type == AVDT_RTCP_PT_SDES)) ) {
1145         result = AVDT_NO_RESOURCES;
1146 
1147         /* build SR - assume fit in one packet */
1148         p_tbl = avdt_ad_tc_tbl_by_type(AVDT_CHAN_REPORT, p_scb->p_ccb, p_scb);
1149         if ((p_tbl->state == AVDT_AD_ST_OPEN) &&
1150                 (p_pkt = (BT_HDR *)osi_malloc(p_tbl->peer_mtu)) != NULL) {
1151             p_pkt->offset = L2CAP_MIN_OFFSET;
1152             p = (UINT8 *)(p_pkt + 1) + p_pkt->offset;
1153 #if AVDT_MULTIPLEXING == TRUE
1154             if (p_scb->curr_cfg.psc_mask & AVDT_PSC_MUX) {
1155                 /* Adaptation Layer header later */
1156                 p_al = p;
1157                 p += 2;
1158             }
1159 #endif
1160             pm1 = p;
1161             *p++ = AVDT_MEDIA_OCTET1 | 1;
1162             *p++ = type;
1163             /* save the location for length */
1164             plen = p;
1165             p += 2;
1166             ssrc = avdt_scb_gen_ssrc(p_scb);
1167             UINT32_TO_BE_STREAM(p, ssrc);
1168 
1169             switch (type) {
1170             case AVDT_RTCP_PT_SR:   /* Sender Report */
1171                 *pm1 = AVDT_MEDIA_OCTET1;
1172                 UINT32_TO_BE_STREAM(p, p_data->sr.ntp_sec);
1173                 UINT32_TO_BE_STREAM(p, p_data->sr.ntp_frac);
1174                 UINT32_TO_BE_STREAM(p, p_data->sr.rtp_time);
1175                 UINT32_TO_BE_STREAM(p, p_data->sr.pkt_count);
1176                 UINT32_TO_BE_STREAM(p, p_data->sr.octet_count);
1177                 break;
1178 
1179             case AVDT_RTCP_PT_RR:   /* Receiver Report */
1180                 *p++ = p_data->rr.frag_lost;
1181                 AVDT_TRACE_API("packet_lost: %d\n", p_data->rr.packet_lost);
1182                 p_data->rr.packet_lost &= 0xFFFFFF;
1183                 AVDT_TRACE_API("packet_lost: %d\n", p_data->rr.packet_lost);
1184                 UINT24_TO_BE_STREAM(p, p_data->rr.packet_lost);
1185                 UINT32_TO_BE_STREAM(p, p_data->rr.seq_num_rcvd);
1186                 UINT32_TO_BE_STREAM(p, p_data->rr.jitter);
1187                 UINT32_TO_BE_STREAM(p, p_data->rr.lsr);
1188                 UINT32_TO_BE_STREAM(p, p_data->rr.dlsr);
1189                 break;
1190 
1191             case AVDT_RTCP_PT_SDES: /* Source Description */
1192                 *p++ = AVDT_RTCP_SDES_CNAME;
1193                 len = strlen((char *)p_data->cname);
1194                 if (len > AVDT_MAX_CNAME_SIZE) {
1195                     len = AVDT_MAX_CNAME_SIZE;
1196                 }
1197                 *p++ = (UINT8)len;
1198                 BCM_STRNCPY_S((char *)p, (char *)p_data->cname, AVDT_MAX_CNAME_SIZE + 1);
1199                 p += len;
1200                 break;
1201             }
1202             p_end = p;
1203             len = p - pm1 - 1;
1204             UINT16_TO_BE_STREAM(plen, len);
1205 
1206 #if AVDT_MULTIPLEXING == TRUE
1207             if (p_scb->curr_cfg.psc_mask & AVDT_PSC_MUX) {
1208                 /* Adaptation Layer header */
1209                 p = p_al;
1210                 len++;
1211                 UINT16_TO_BE_STREAM(p_al, len );
1212                 /* TSID, no-fragment bit and coding of length(9-bit length field) */
1213                 u = *p;
1214                 *p = (p_scb->curr_cfg.mux_tsid_report << 3) | AVDT_ALH_LCODE_9BITM0;
1215                 if (u) {
1216                     *p |= AVDT_ALH_LCODE_9BITM1;
1217                 }
1218             }
1219 #endif
1220 
1221             /* set the actual payload length */
1222             p_pkt->len = p_end - p;
1223             /* send the packet */
1224             if (L2CAP_DW_FAILED != avdt_ad_write_req(AVDT_CHAN_REPORT, p_scb->p_ccb, p_scb, p_pkt)) {
1225                 result = AVDT_SUCCESS;
1226             }
1227         }
1228     }
1229 
1230     return result;
1231 }
1232 #endif
1233 
1234 /******************************************************************************
1235 **
1236 ** Function         AVDT_SetTraceLevel
1237 **
1238 ** Description      Sets the trace level for AVDT. If 0xff is passed, the
1239 **                  current trace level is returned.
1240 **
1241 **                  Input Parameters:
1242 **                      new_level:  The level to set the AVDT tracing to:
1243 **                      0xff-returns the current setting.
1244 **                      0-turns off tracing.
1245 **                      >= 1-Errors.
1246 **                      >= 2-Warnings.
1247 **                      >= 3-APIs.
1248 **                      >= 4-Events.
1249 **                      >= 5-Debug.
1250 **
1251 ** Returns          The new trace level or current trace level if
1252 **                  the input parameter is 0xff.
1253 **
1254 ******************************************************************************/
AVDT_SetTraceLevel(UINT8 new_level)1255 UINT8 AVDT_SetTraceLevel (UINT8 new_level)
1256 {
1257     if (new_level != 0xFF) {
1258         avdt_cb.trace_level = new_level;
1259     }
1260 
1261     return (avdt_cb.trace_level);
1262 }
1263 
1264 #endif /*  #if (defined(AVDT_INCLUDED) && AVDT_INCLUDED == TRUE) */
1265