1 /*
2  * Copyright 2016 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 /******************************************************************************
18  *
19  *  Utility functions to help build and parse the aptX-HD Codec Information
20  *  Element and Media Payload.
21  *
22  ******************************************************************************/
23 
24 #define LOG_TAG "bluetooth-a2dp"
25 
26 #include "a2dp_vendor_aptx_hd.h"
27 
28 #include <bluetooth/log.h>
29 #include <string.h>
30 
31 #include "a2dp_vendor.h"
32 #include "a2dp_vendor_aptx_hd_encoder.h"
33 #include "btif/include/btif_av_co.h"
34 #include "internal_include/bt_trace.h"
35 #include "os/log.h"
36 #include "osi/include/osi.h"
37 #include "stack/include/bt_hdr.h"
38 
39 using namespace bluetooth;
40 
41 // data type for the aptX-HD Codec Information Element */
42 typedef struct {
43   uint32_t vendorId;
44   uint16_t codecId;    /* Codec ID for aptX-HD */
45   uint8_t sampleRate;  /* Sampling Frequency */
46   uint8_t channelMode; /* STEREO/DUAL/MONO */
47   uint8_t acl_sprint_reserved0;
48   uint8_t acl_sprint_reserved1;
49   uint8_t acl_sprint_reserved2;
50   uint8_t acl_sprint_reserved3;
51   btav_a2dp_codec_bits_per_sample_t bits_per_sample;
52 } tA2DP_APTX_HD_CIE;
53 
54 /* aptX-HD Source codec capabilities */
55 static const tA2DP_APTX_HD_CIE a2dp_aptx_hd_source_caps = {
56     A2DP_APTX_HD_VENDOR_ID,          /* vendorId */
57     A2DP_APTX_HD_CODEC_ID_BLUETOOTH, /* codecId */
58     (A2DP_APTX_HD_SAMPLERATE_44100 |
59      A2DP_APTX_HD_SAMPLERATE_48000),   /* sampleRate */
60     A2DP_APTX_HD_CHANNELS_STEREO,      /* channelMode */
61     A2DP_APTX_HD_ACL_SPRINT_RESERVED0, /* acl_sprint_reserved0 */
62     A2DP_APTX_HD_ACL_SPRINT_RESERVED1, /* acl_sprint_reserved1 */
63     A2DP_APTX_HD_ACL_SPRINT_RESERVED2, /* acl_sprint_reserved2 */
64     A2DP_APTX_HD_ACL_SPRINT_RESERVED3, /* acl_sprint_reserved3 */
65     BTAV_A2DP_CODEC_BITS_PER_SAMPLE_24 /* bits_per_sample */
66 };
67 
68 /* Default aptX-HD codec configuration */
69 static const tA2DP_APTX_HD_CIE a2dp_aptx_hd_default_config = {
70     A2DP_APTX_HD_VENDOR_ID,            /* vendorId */
71     A2DP_APTX_HD_CODEC_ID_BLUETOOTH,   /* codecId */
72     A2DP_APTX_HD_SAMPLERATE_48000,     /* sampleRate */
73     A2DP_APTX_HD_CHANNELS_STEREO,      /* channelMode */
74     A2DP_APTX_HD_ACL_SPRINT_RESERVED0, /* acl_sprint_reserved0 */
75     A2DP_APTX_HD_ACL_SPRINT_RESERVED1, /* acl_sprint_reserved1 */
76     A2DP_APTX_HD_ACL_SPRINT_RESERVED2, /* acl_sprint_reserved2 */
77     A2DP_APTX_HD_ACL_SPRINT_RESERVED3, /* acl_sprint_reserved3 */
78     BTAV_A2DP_CODEC_BITS_PER_SAMPLE_24 /* bits_per_sample */
79 };
80 
81 static const tA2DP_ENCODER_INTERFACE a2dp_encoder_interface_aptx_hd = {
82     a2dp_vendor_aptx_hd_encoder_init,
83     a2dp_vendor_aptx_hd_encoder_cleanup,
84     a2dp_vendor_aptx_hd_feeding_reset,
85     a2dp_vendor_aptx_hd_feeding_flush,
86     a2dp_vendor_aptx_hd_get_encoder_interval_ms,
87     a2dp_vendor_aptx_hd_get_effective_frame_size,
88     a2dp_vendor_aptx_hd_send_frames,
89     nullptr  // set_transmit_queue_length
90 };
91 
92 static tA2DP_STATUS A2DP_CodecInfoMatchesCapabilityAptxHd(
93     const tA2DP_APTX_HD_CIE* p_cap, const uint8_t* p_codec_info,
94     bool is_peer_codec_info);
95 
96 // Builds the aptX-HD Media Codec Capabilities byte sequence beginning from the
97 // LOSC octet. |media_type| is the media type |AVDT_MEDIA_TYPE_*|.
98 // |p_ie| is a pointer to the aptX-HD Codec Information Element information.
99 // The result is stored in |p_result|. Returns A2DP_SUCCESS on success,
100 // otherwise the corresponding A2DP error status code.
A2DP_BuildInfoAptxHd(uint8_t media_type,const tA2DP_APTX_HD_CIE * p_ie,uint8_t * p_result)101 static tA2DP_STATUS A2DP_BuildInfoAptxHd(uint8_t media_type,
102                                          const tA2DP_APTX_HD_CIE* p_ie,
103                                          uint8_t* p_result) {
104   if (p_ie == NULL || p_result == NULL) {
105     return A2DP_INVALID_PARAMS;
106   }
107 
108   *p_result++ = A2DP_APTX_HD_CODEC_LEN;
109   *p_result++ = (media_type << 4);
110   *p_result++ = A2DP_MEDIA_CT_NON_A2DP;
111   *p_result++ = (uint8_t)(p_ie->vendorId & 0x000000FF);
112   *p_result++ = (uint8_t)((p_ie->vendorId & 0x0000FF00) >> 8);
113   *p_result++ = (uint8_t)((p_ie->vendorId & 0x00FF0000) >> 16);
114   *p_result++ = (uint8_t)((p_ie->vendorId & 0xFF000000) >> 24);
115   *p_result++ = (uint8_t)(p_ie->codecId & 0x00FF);
116   *p_result++ = (uint8_t)((p_ie->codecId & 0xFF00) >> 8);
117   *p_result++ = p_ie->sampleRate | p_ie->channelMode;
118   *p_result++ = p_ie->acl_sprint_reserved0;
119   *p_result++ = p_ie->acl_sprint_reserved1;
120   *p_result++ = p_ie->acl_sprint_reserved2;
121   *p_result++ = p_ie->acl_sprint_reserved3;
122 
123   return A2DP_SUCCESS;
124 }
125 
126 // Parses the aptX-HD Media Codec Capabilities byte sequence beginning from the
127 // LOSC octet. The result is stored in |p_ie|. The byte sequence to parse is
128 // |p_codec_info|. If |is_capability| is true, the byte sequence is
129 // codec capabilities, otherwise is codec configuration.
130 // Returns A2DP_SUCCESS on success, otherwise the corresponding A2DP error
131 // status code.
A2DP_ParseInfoAptxHd(tA2DP_APTX_HD_CIE * p_ie,const uint8_t * p_codec_info,bool is_capability)132 static tA2DP_STATUS A2DP_ParseInfoAptxHd(tA2DP_APTX_HD_CIE* p_ie,
133                                          const uint8_t* p_codec_info,
134                                          bool is_capability) {
135   uint8_t losc;
136   uint8_t media_type;
137   tA2DP_CODEC_TYPE codec_type;
138 
139   if (p_ie == NULL || p_codec_info == NULL) return A2DP_INVALID_PARAMS;
140 
141   // Check the codec capability length
142   losc = *p_codec_info++;
143   if (losc != A2DP_APTX_HD_CODEC_LEN) return A2DP_WRONG_CODEC;
144 
145   media_type = (*p_codec_info++) >> 4;
146   codec_type = *p_codec_info++;
147   /* Check the Media Type and Media Codec Type */
148   if (media_type != AVDT_MEDIA_TYPE_AUDIO ||
149       codec_type != A2DP_MEDIA_CT_NON_A2DP) {
150     return A2DP_WRONG_CODEC;
151   }
152 
153   // Check the Vendor ID and Codec ID */
154   p_ie->vendorId = (*p_codec_info & 0x000000FF) |
155                    (*(p_codec_info + 1) << 8 & 0x0000FF00) |
156                    (*(p_codec_info + 2) << 16 & 0x00FF0000) |
157                    (*(p_codec_info + 3) << 24 & 0xFF000000);
158   p_codec_info += 4;
159   p_ie->codecId =
160       (*p_codec_info & 0x00FF) | (*(p_codec_info + 1) << 8 & 0xFF00);
161   p_codec_info += 2;
162   if (p_ie->vendorId != A2DP_APTX_HD_VENDOR_ID ||
163       p_ie->codecId != A2DP_APTX_HD_CODEC_ID_BLUETOOTH) {
164     return A2DP_WRONG_CODEC;
165   }
166 
167   p_ie->channelMode = *p_codec_info & 0x0F;
168   p_ie->sampleRate = *p_codec_info & 0xF0;
169   p_codec_info++;
170 
171   p_ie->acl_sprint_reserved0 = *(p_codec_info++);
172   p_ie->acl_sprint_reserved1 = *(p_codec_info++);
173   p_ie->acl_sprint_reserved2 = *(p_codec_info++);
174   p_ie->acl_sprint_reserved3 = *(p_codec_info++);
175 
176   if (is_capability) {
177     // NOTE: The checks here are very liberal. We should be using more
178     // pedantic checks specific to the SRC or SNK as specified in the spec.
179     if (A2DP_BitsSet(p_ie->sampleRate) == A2DP_SET_ZERO_BIT)
180       return A2DP_BAD_SAMP_FREQ;
181     if (A2DP_BitsSet(p_ie->channelMode) == A2DP_SET_ZERO_BIT)
182       return A2DP_BAD_CH_MODE;
183 
184     return A2DP_SUCCESS;
185   }
186 
187   if (A2DP_BitsSet(p_ie->sampleRate) != A2DP_SET_ONE_BIT)
188     return A2DP_BAD_SAMP_FREQ;
189   if (A2DP_BitsSet(p_ie->channelMode) != A2DP_SET_ONE_BIT)
190     return A2DP_BAD_CH_MODE;
191 
192   return A2DP_SUCCESS;
193 }
194 
A2DP_IsVendorSourceCodecValidAptxHd(const uint8_t * p_codec_info)195 bool A2DP_IsVendorSourceCodecValidAptxHd(const uint8_t* p_codec_info) {
196   tA2DP_APTX_HD_CIE cfg_cie;
197 
198   /* Use a liberal check when parsing the codec info */
199   return (A2DP_ParseInfoAptxHd(&cfg_cie, p_codec_info, false) ==
200           A2DP_SUCCESS) ||
201          (A2DP_ParseInfoAptxHd(&cfg_cie, p_codec_info, true) == A2DP_SUCCESS);
202 }
203 
A2DP_IsVendorPeerSinkCodecValidAptxHd(const uint8_t * p_codec_info)204 bool A2DP_IsVendorPeerSinkCodecValidAptxHd(const uint8_t* p_codec_info) {
205   tA2DP_APTX_HD_CIE cfg_cie;
206 
207   /* Use a liberal check when parsing the codec info */
208   return (A2DP_ParseInfoAptxHd(&cfg_cie, p_codec_info, false) ==
209           A2DP_SUCCESS) ||
210          (A2DP_ParseInfoAptxHd(&cfg_cie, p_codec_info, true) == A2DP_SUCCESS);
211 }
212 
213 // Checks whether A2DP aptX-HD codec configuration matches with a device's
214 // codec capabilities. |p_cap| is the aptX-HD codec configuration.
215 // |p_codec_info| is the device's codec capabilities.
216 // If |is_capability| is true, the byte sequence is codec capabilities,
217 // otherwise is codec configuration.
218 // |p_codec_info| contains the codec capabilities for a peer device that
219 // is acting as an A2DP source.
220 // Returns A2DP_SUCCESS if the codec configuration matches with capabilities,
221 // otherwise the corresponding A2DP error status code.
A2DP_CodecInfoMatchesCapabilityAptxHd(const tA2DP_APTX_HD_CIE * p_cap,const uint8_t * p_codec_info,bool is_capability)222 UNUSED_ATTR static tA2DP_STATUS A2DP_CodecInfoMatchesCapabilityAptxHd(
223     const tA2DP_APTX_HD_CIE* p_cap, const uint8_t* p_codec_info,
224     bool is_capability) {
225   tA2DP_STATUS status;
226   tA2DP_APTX_HD_CIE cfg_cie;
227 
228   /* parse configuration */
229   status = A2DP_ParseInfoAptxHd(&cfg_cie, p_codec_info, is_capability);
230   if (status != A2DP_SUCCESS) {
231     log::error("parsing failed {}", status);
232     return status;
233   }
234 
235   /* verify that each parameter is in range */
236 
237   log::verbose("FREQ peer: 0x{:x}, capability 0x{:x}", cfg_cie.sampleRate,
238                p_cap->sampleRate);
239   log::verbose("CH_MODE peer: 0x{:x}, capability 0x{:x}", cfg_cie.channelMode,
240                p_cap->channelMode);
241 
242   /* sampling frequency */
243   if ((cfg_cie.sampleRate & p_cap->sampleRate) == 0) return A2DP_NS_SAMP_FREQ;
244 
245   /* channel mode */
246   if ((cfg_cie.channelMode & p_cap->channelMode) == 0) return A2DP_NS_CH_MODE;
247 
248   return A2DP_SUCCESS;
249 }
250 
A2DP_VendorUsesRtpHeaderAptxHd(bool,const uint8_t *)251 bool A2DP_VendorUsesRtpHeaderAptxHd(bool /* content_protection_enabled */,
252                                     const uint8_t* /* p_codec_info */) {
253   return true;
254 }
255 
A2DP_VendorCodecNameAptxHd(const uint8_t *)256 const char* A2DP_VendorCodecNameAptxHd(const uint8_t* /* p_codec_info */) {
257   return "aptX-HD";
258 }
259 
A2DP_VendorCodecTypeEqualsAptxHd(const uint8_t * p_codec_info_a,const uint8_t * p_codec_info_b)260 bool A2DP_VendorCodecTypeEqualsAptxHd(const uint8_t* p_codec_info_a,
261                                       const uint8_t* p_codec_info_b) {
262   tA2DP_APTX_HD_CIE aptx_hd_cie_a;
263   tA2DP_APTX_HD_CIE aptx_hd_cie_b;
264 
265   // Check whether the codec info contains valid data
266   tA2DP_STATUS a2dp_status =
267       A2DP_ParseInfoAptxHd(&aptx_hd_cie_a, p_codec_info_a, true);
268   if (a2dp_status != A2DP_SUCCESS) {
269     log::error("cannot decode codec information: {}", a2dp_status);
270     return false;
271   }
272   a2dp_status = A2DP_ParseInfoAptxHd(&aptx_hd_cie_b, p_codec_info_b, true);
273   if (a2dp_status != A2DP_SUCCESS) {
274     log::error("cannot decode codec information: {}", a2dp_status);
275     return false;
276   }
277 
278   return true;
279 }
280 
A2DP_VendorCodecEqualsAptxHd(const uint8_t * p_codec_info_a,const uint8_t * p_codec_info_b)281 bool A2DP_VendorCodecEqualsAptxHd(const uint8_t* p_codec_info_a,
282                                   const uint8_t* p_codec_info_b) {
283   tA2DP_APTX_HD_CIE aptx_hd_cie_a;
284   tA2DP_APTX_HD_CIE aptx_hd_cie_b;
285 
286   // Check whether the codec info contains valid data
287   tA2DP_STATUS a2dp_status =
288       A2DP_ParseInfoAptxHd(&aptx_hd_cie_a, p_codec_info_a, true);
289   if (a2dp_status != A2DP_SUCCESS) {
290     log::error("cannot decode codec information: {}", a2dp_status);
291     return false;
292   }
293   a2dp_status = A2DP_ParseInfoAptxHd(&aptx_hd_cie_b, p_codec_info_b, true);
294   if (a2dp_status != A2DP_SUCCESS) {
295     log::error("cannot decode codec information: {}", a2dp_status);
296     return false;
297   }
298 
299   return (aptx_hd_cie_a.sampleRate == aptx_hd_cie_b.sampleRate) &&
300          (aptx_hd_cie_a.channelMode == aptx_hd_cie_b.channelMode);
301 }
302 
A2DP_VendorGetBitRateAptxHd(const uint8_t * p_codec_info)303 int A2DP_VendorGetBitRateAptxHd(const uint8_t* p_codec_info) {
304   A2dpCodecConfig* CodecConfig = bta_av_get_a2dp_current_codec();
305   tA2DP_BITS_PER_SAMPLE bits_per_sample = CodecConfig->getAudioBitsPerSample();
306   uint16_t samplerate = A2DP_GetTrackSampleRate(p_codec_info);
307   return (samplerate * bits_per_sample * 2) / 4;
308 }
309 
A2DP_VendorGetTrackSampleRateAptxHd(const uint8_t * p_codec_info)310 int A2DP_VendorGetTrackSampleRateAptxHd(const uint8_t* p_codec_info) {
311   tA2DP_APTX_HD_CIE aptx_hd_cie;
312 
313   // Check whether the codec info contains valid data
314   tA2DP_STATUS a2dp_status =
315       A2DP_ParseInfoAptxHd(&aptx_hd_cie, p_codec_info, false);
316   if (a2dp_status != A2DP_SUCCESS) {
317     log::error("cannot decode codec information: {}", a2dp_status);
318     return -1;
319   }
320 
321   if (aptx_hd_cie.sampleRate == A2DP_APTX_HD_SAMPLERATE_44100) return 44100;
322   if (aptx_hd_cie.sampleRate == A2DP_APTX_HD_SAMPLERATE_48000) return 48000;
323 
324   return -1;
325 }
326 
A2DP_VendorGetTrackBitsPerSampleAptxHd(const uint8_t * p_codec_info)327 int A2DP_VendorGetTrackBitsPerSampleAptxHd(const uint8_t* p_codec_info) {
328   tA2DP_APTX_HD_CIE aptx_hd_cie;
329 
330   // Check whether the codec info contains valid data
331   tA2DP_STATUS a2dp_status =
332       A2DP_ParseInfoAptxHd(&aptx_hd_cie, p_codec_info, false);
333   if (a2dp_status != A2DP_SUCCESS) {
334     log::error("cannot decode codec information: {}", a2dp_status);
335     return -1;
336   }
337 
338   // NOTE: The bits per sample never changes for aptX-HD
339   return 24;
340 }
341 
A2DP_VendorGetTrackChannelCountAptxHd(const uint8_t * p_codec_info)342 int A2DP_VendorGetTrackChannelCountAptxHd(const uint8_t* p_codec_info) {
343   tA2DP_APTX_HD_CIE aptx_hd_cie;
344 
345   // Check whether the codec info contains valid data
346   tA2DP_STATUS a2dp_status =
347       A2DP_ParseInfoAptxHd(&aptx_hd_cie, p_codec_info, false);
348   if (a2dp_status != A2DP_SUCCESS) {
349     log::error("cannot decode codec information: {}", a2dp_status);
350     return -1;
351   }
352 
353   switch (aptx_hd_cie.channelMode) {
354     case A2DP_APTX_HD_CHANNELS_MONO:
355       return 1;
356     case A2DP_APTX_HD_CHANNELS_STEREO:
357       return 2;
358   }
359 
360   return -1;
361 }
362 
A2DP_VendorGetPacketTimestampAptxHd(const uint8_t *,const uint8_t * p_data,uint32_t * p_timestamp)363 bool A2DP_VendorGetPacketTimestampAptxHd(const uint8_t* /* p_codec_info */,
364                                          const uint8_t* p_data,
365                                          uint32_t* p_timestamp) {
366   // TODO: Is this function really codec-specific?
367   *p_timestamp = *(const uint32_t*)p_data;
368   return true;
369 }
370 
A2DP_VendorBuildCodecHeaderAptxHd(const uint8_t *,BT_HDR *,uint16_t)371 bool A2DP_VendorBuildCodecHeaderAptxHd(const uint8_t* /* p_codec_info */,
372                                        BT_HDR* /* p_buf */,
373                                        uint16_t /* frames_per_packet */) {
374   // Nothing to do
375   return true;
376 }
377 
A2DP_VendorCodecInfoStringAptxHd(const uint8_t * p_codec_info)378 std::string A2DP_VendorCodecInfoStringAptxHd(const uint8_t* p_codec_info) {
379   std::stringstream res;
380   std::string field;
381   tA2DP_STATUS a2dp_status;
382   tA2DP_APTX_HD_CIE aptx_hd_cie;
383 
384   a2dp_status = A2DP_ParseInfoAptxHd(&aptx_hd_cie, p_codec_info, true);
385   if (a2dp_status != A2DP_SUCCESS) {
386     res << "A2DP_ParseInfoAptxHd fail: "
387         << loghex(static_cast<uint8_t>(a2dp_status));
388     return res.str();
389   }
390 
391   res << "\tname: aptX-HD\n";
392 
393   // Sample frequency
394   field.clear();
395   AppendField(&field, (aptx_hd_cie.sampleRate == 0), "NONE");
396   AppendField(&field, (aptx_hd_cie.sampleRate & A2DP_APTX_HD_SAMPLERATE_44100),
397               "44100");
398   AppendField(&field, (aptx_hd_cie.sampleRate & A2DP_APTX_HD_SAMPLERATE_48000),
399               "48000");
400   res << "\tsamp_freq: " << field << " (" << loghex(aptx_hd_cie.sampleRate)
401       << ")\n";
402 
403   // Channel mode
404   field.clear();
405   AppendField(&field, (aptx_hd_cie.channelMode == 0), "NONE");
406   AppendField(&field, (aptx_hd_cie.channelMode & A2DP_APTX_HD_CHANNELS_MONO),
407               "Mono");
408   AppendField(&field, (aptx_hd_cie.channelMode & A2DP_APTX_HD_CHANNELS_STEREO),
409               "Stereo");
410   res << "\tch_mode: " << field << " (" << loghex(aptx_hd_cie.channelMode)
411       << ")\n";
412 
413   return res.str();
414 }
415 
A2DP_VendorGetEncoderInterfaceAptxHd(const uint8_t * p_codec_info)416 const tA2DP_ENCODER_INTERFACE* A2DP_VendorGetEncoderInterfaceAptxHd(
417     const uint8_t* p_codec_info) {
418   if (!A2DP_IsVendorSourceCodecValidAptxHd(p_codec_info)) return NULL;
419 
420   return &a2dp_encoder_interface_aptx_hd;
421 }
422 
A2DP_VendorAdjustCodecAptxHd(uint8_t * p_codec_info)423 bool A2DP_VendorAdjustCodecAptxHd(uint8_t* p_codec_info) {
424   tA2DP_APTX_HD_CIE cfg_cie;
425 
426   // Nothing to do: just verify the codec info is valid
427   if (A2DP_ParseInfoAptxHd(&cfg_cie, p_codec_info, true) != A2DP_SUCCESS)
428     return false;
429 
430   return true;
431 }
432 
A2DP_VendorSourceCodecIndexAptxHd(const uint8_t * p_codec_info)433 btav_a2dp_codec_index_t A2DP_VendorSourceCodecIndexAptxHd(
434     const uint8_t* p_codec_info) {
435   return BTAV_A2DP_CODEC_INDEX_SOURCE_APTX_HD;
436 }
437 
A2DP_VendorCodecIndexStrAptxHd(void)438 const char* A2DP_VendorCodecIndexStrAptxHd(void) { return "aptX-HD"; }
439 
A2DP_VendorInitCodecConfigAptxHd(AvdtpSepConfig * p_cfg)440 bool A2DP_VendorInitCodecConfigAptxHd(AvdtpSepConfig* p_cfg) {
441   if (A2DP_BuildInfoAptxHd(AVDT_MEDIA_TYPE_AUDIO, &a2dp_aptx_hd_source_caps,
442                            p_cfg->codec_info) != A2DP_SUCCESS) {
443     return false;
444   }
445 
446   return true;
447 }
448 
A2dpCodecConfigAptxHd(btav_a2dp_codec_priority_t codec_priority)449 A2dpCodecConfigAptxHd::A2dpCodecConfigAptxHd(
450     btav_a2dp_codec_priority_t codec_priority)
451     : A2dpCodecConfig(BTAV_A2DP_CODEC_INDEX_SOURCE_APTX_HD,
452                       A2DP_CODEC_ID_APTX_HD, A2DP_VendorCodecIndexStrAptxHd(),
453                       codec_priority) {
454   // Compute the local capability
455   if (a2dp_aptx_hd_source_caps.sampleRate & A2DP_APTX_HD_SAMPLERATE_44100) {
456     codec_local_capability_.sample_rate |= BTAV_A2DP_CODEC_SAMPLE_RATE_44100;
457   }
458   if (a2dp_aptx_hd_source_caps.sampleRate & A2DP_APTX_HD_SAMPLERATE_48000) {
459     codec_local_capability_.sample_rate |= BTAV_A2DP_CODEC_SAMPLE_RATE_48000;
460   }
461   codec_local_capability_.bits_per_sample =
462       a2dp_aptx_hd_source_caps.bits_per_sample;
463   if (a2dp_aptx_hd_source_caps.channelMode & A2DP_APTX_HD_CHANNELS_MONO) {
464     codec_local_capability_.channel_mode |= BTAV_A2DP_CODEC_CHANNEL_MODE_MONO;
465   }
466   if (a2dp_aptx_hd_source_caps.channelMode & A2DP_APTX_HD_CHANNELS_STEREO) {
467     codec_local_capability_.channel_mode |= BTAV_A2DP_CODEC_CHANNEL_MODE_STEREO;
468   }
469 }
470 
~A2dpCodecConfigAptxHd()471 A2dpCodecConfigAptxHd::~A2dpCodecConfigAptxHd() {}
472 
init()473 bool A2dpCodecConfigAptxHd::init() {
474   if (!isValid()) return false;
475 
476   // Load the encoder
477   if (A2DP_VendorLoadEncoderAptxHd() != LOAD_SUCCESS) {
478     log::error("cannot load the encoder");
479     return false;
480   }
481 
482   return true;
483 }
484 
useRtpHeaderMarkerBit() const485 bool A2dpCodecConfigAptxHd::useRtpHeaderMarkerBit() const { return false; }
486 
487 //
488 // Selects the best sample rate from |sampleRate|.
489 // The result is stored in |p_result| and p_codec_config|.
490 // Returns true if a selection was made, otherwise false.
491 //
select_best_sample_rate(uint8_t sampleRate,tA2DP_APTX_HD_CIE * p_result,btav_a2dp_codec_config_t * p_codec_config)492 static bool select_best_sample_rate(uint8_t sampleRate,
493                                     tA2DP_APTX_HD_CIE* p_result,
494                                     btav_a2dp_codec_config_t* p_codec_config) {
495   if (sampleRate & A2DP_APTX_HD_SAMPLERATE_48000) {
496     p_result->sampleRate = A2DP_APTX_HD_SAMPLERATE_48000;
497     p_codec_config->sample_rate = BTAV_A2DP_CODEC_SAMPLE_RATE_48000;
498     return true;
499   }
500   if (sampleRate & A2DP_APTX_HD_SAMPLERATE_44100) {
501     p_result->sampleRate = A2DP_APTX_HD_SAMPLERATE_44100;
502     p_codec_config->sample_rate = BTAV_A2DP_CODEC_SAMPLE_RATE_44100;
503     return true;
504   }
505   return false;
506 }
507 
508 //
509 // Selects the audio sample rate from |p_codec_audio_config|.
510 // |sampleRate| contains the capability.
511 // The result is stored in |p_result| and |p_codec_config|.
512 // Returns true if a selection was made, otherwise false.
513 //
select_audio_sample_rate(const btav_a2dp_codec_config_t * p_codec_audio_config,uint8_t sampleRate,tA2DP_APTX_HD_CIE * p_result,btav_a2dp_codec_config_t * p_codec_config)514 static bool select_audio_sample_rate(
515     const btav_a2dp_codec_config_t* p_codec_audio_config, uint8_t sampleRate,
516     tA2DP_APTX_HD_CIE* p_result, btav_a2dp_codec_config_t* p_codec_config) {
517   switch (p_codec_audio_config->sample_rate) {
518     case BTAV_A2DP_CODEC_SAMPLE_RATE_44100:
519       if (sampleRate & A2DP_APTX_HD_SAMPLERATE_44100) {
520         p_result->sampleRate = A2DP_APTX_HD_SAMPLERATE_44100;
521         p_codec_config->sample_rate = BTAV_A2DP_CODEC_SAMPLE_RATE_44100;
522         return true;
523       }
524       break;
525     case BTAV_A2DP_CODEC_SAMPLE_RATE_48000:
526       if (sampleRate & A2DP_APTX_HD_SAMPLERATE_48000) {
527         p_result->sampleRate = A2DP_APTX_HD_SAMPLERATE_48000;
528         p_codec_config->sample_rate = BTAV_A2DP_CODEC_SAMPLE_RATE_48000;
529         return true;
530       }
531       break;
532     case BTAV_A2DP_CODEC_SAMPLE_RATE_88200:
533     case BTAV_A2DP_CODEC_SAMPLE_RATE_96000:
534     case BTAV_A2DP_CODEC_SAMPLE_RATE_176400:
535     case BTAV_A2DP_CODEC_SAMPLE_RATE_192000:
536     case BTAV_A2DP_CODEC_SAMPLE_RATE_16000:
537     case BTAV_A2DP_CODEC_SAMPLE_RATE_24000:
538     case BTAV_A2DP_CODEC_SAMPLE_RATE_NONE:
539       break;
540   }
541   return false;
542 }
543 
544 //
545 // Selects the best bits per sample.
546 // The result is stored in |p_codec_config|.
547 // Returns true if a selection was made, otherwise false.
548 //
select_best_bits_per_sample(btav_a2dp_codec_config_t * p_codec_config)549 static bool select_best_bits_per_sample(
550     btav_a2dp_codec_config_t* p_codec_config) {
551   p_codec_config->bits_per_sample = BTAV_A2DP_CODEC_BITS_PER_SAMPLE_24;
552   return true;
553 }
554 
555 //
556 // Selects the audio bits per sample from |p_codec_audio_config|.
557 // The result is stored in |p_codec_config|.
558 // Returns true if a selection was made, otherwise false.
559 //
select_audio_bits_per_sample(const btav_a2dp_codec_config_t * p_codec_audio_config,btav_a2dp_codec_config_t * p_codec_config)560 static bool select_audio_bits_per_sample(
561     const btav_a2dp_codec_config_t* p_codec_audio_config,
562     btav_a2dp_codec_config_t* p_codec_config) {
563   switch (p_codec_audio_config->bits_per_sample) {
564     case BTAV_A2DP_CODEC_BITS_PER_SAMPLE_24:
565       p_codec_config->bits_per_sample = BTAV_A2DP_CODEC_BITS_PER_SAMPLE_24;
566       return true;
567     case BTAV_A2DP_CODEC_BITS_PER_SAMPLE_16:
568     case BTAV_A2DP_CODEC_BITS_PER_SAMPLE_32:
569     case BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE:
570       break;
571   }
572   return false;
573 }
574 
575 //
576 // Selects the best channel mode from |channelMode|.
577 // The result is stored in |p_result| and |p_codec_config|.
578 // Returns true if a selection was made, otherwise false.
579 //
select_best_channel_mode(uint8_t channelMode,tA2DP_APTX_HD_CIE * p_result,btav_a2dp_codec_config_t * p_codec_config)580 static bool select_best_channel_mode(uint8_t channelMode,
581                                      tA2DP_APTX_HD_CIE* p_result,
582                                      btav_a2dp_codec_config_t* p_codec_config) {
583   if (channelMode & A2DP_APTX_HD_CHANNELS_STEREO) {
584     p_result->channelMode = A2DP_APTX_HD_CHANNELS_STEREO;
585     p_codec_config->channel_mode = BTAV_A2DP_CODEC_CHANNEL_MODE_STEREO;
586     return true;
587   }
588   if (channelMode & A2DP_APTX_HD_CHANNELS_MONO) {
589     p_result->channelMode = A2DP_APTX_HD_CHANNELS_MONO;
590     p_codec_config->channel_mode = BTAV_A2DP_CODEC_CHANNEL_MODE_MONO;
591     return true;
592   }
593   return false;
594 }
595 
596 //
597 // Selects the audio channel mode from |p_codec_audio_config|.
598 // |channelMode| contains the capability.
599 // The result is stored in |p_result| and |p_codec_config|.
600 // Returns true if a selection was made, otherwise false.
601 //
select_audio_channel_mode(const btav_a2dp_codec_config_t * p_codec_audio_config,uint8_t channelMode,tA2DP_APTX_HD_CIE * p_result,btav_a2dp_codec_config_t * p_codec_config)602 static bool select_audio_channel_mode(
603     const btav_a2dp_codec_config_t* p_codec_audio_config, uint8_t channelMode,
604     tA2DP_APTX_HD_CIE* p_result, btav_a2dp_codec_config_t* p_codec_config) {
605   switch (p_codec_audio_config->channel_mode) {
606     case BTAV_A2DP_CODEC_CHANNEL_MODE_MONO:
607       if (channelMode & A2DP_APTX_HD_CHANNELS_MONO) {
608         p_result->channelMode = A2DP_APTX_HD_CHANNELS_MONO;
609         p_codec_config->channel_mode = BTAV_A2DP_CODEC_CHANNEL_MODE_MONO;
610         return true;
611       }
612       break;
613     case BTAV_A2DP_CODEC_CHANNEL_MODE_STEREO:
614       if (channelMode & A2DP_APTX_HD_CHANNELS_STEREO) {
615         p_result->channelMode = A2DP_APTX_HD_CHANNELS_STEREO;
616         p_codec_config->channel_mode = BTAV_A2DP_CODEC_CHANNEL_MODE_STEREO;
617         return true;
618       }
619       break;
620     case BTAV_A2DP_CODEC_CHANNEL_MODE_NONE:
621       break;
622   }
623 
624   return false;
625 }
626 
setCodecConfig(const uint8_t * p_peer_codec_info,bool is_capability,uint8_t * p_result_codec_config)627 bool A2dpCodecConfigAptxHd::setCodecConfig(const uint8_t* p_peer_codec_info,
628                                            bool is_capability,
629                                            uint8_t* p_result_codec_config) {
630   std::lock_guard<std::recursive_mutex> lock(codec_mutex_);
631   tA2DP_APTX_HD_CIE peer_info_cie;
632   tA2DP_APTX_HD_CIE result_config_cie;
633   uint8_t sampleRate;
634   uint8_t channelMode;
635 
636   // Save the internal state
637   btav_a2dp_codec_config_t saved_codec_config = codec_config_;
638   btav_a2dp_codec_config_t saved_codec_capability = codec_capability_;
639   btav_a2dp_codec_config_t saved_codec_selectable_capability =
640       codec_selectable_capability_;
641   btav_a2dp_codec_config_t saved_codec_user_config = codec_user_config_;
642   btav_a2dp_codec_config_t saved_codec_audio_config = codec_audio_config_;
643   uint8_t saved_ota_codec_config[AVDT_CODEC_SIZE];
644   uint8_t saved_ota_codec_peer_capability[AVDT_CODEC_SIZE];
645   uint8_t saved_ota_codec_peer_config[AVDT_CODEC_SIZE];
646   memcpy(saved_ota_codec_config, ota_codec_config_, sizeof(ota_codec_config_));
647   memcpy(saved_ota_codec_peer_capability, ota_codec_peer_capability_,
648          sizeof(ota_codec_peer_capability_));
649   memcpy(saved_ota_codec_peer_config, ota_codec_peer_config_,
650          sizeof(ota_codec_peer_config_));
651 
652   tA2DP_STATUS status =
653       A2DP_ParseInfoAptxHd(&peer_info_cie, p_peer_codec_info, is_capability);
654   if (status != A2DP_SUCCESS) {
655     log::error("can't parse peer's capabilities: error = {}", status);
656     goto fail;
657   }
658 
659   //
660   // Build the preferred configuration
661   //
662   memset(&result_config_cie, 0, sizeof(result_config_cie));
663   result_config_cie.vendorId = a2dp_aptx_hd_source_caps.vendorId;
664   result_config_cie.codecId = a2dp_aptx_hd_source_caps.codecId;
665 
666   //
667   // Select the sample frequency
668   //
669   sampleRate = a2dp_aptx_hd_source_caps.sampleRate & peer_info_cie.sampleRate;
670   codec_config_.sample_rate = BTAV_A2DP_CODEC_SAMPLE_RATE_NONE;
671   switch (codec_user_config_.sample_rate) {
672     case BTAV_A2DP_CODEC_SAMPLE_RATE_44100:
673       if (sampleRate & A2DP_APTX_HD_SAMPLERATE_44100) {
674         result_config_cie.sampleRate = A2DP_APTX_HD_SAMPLERATE_44100;
675         codec_capability_.sample_rate = codec_user_config_.sample_rate;
676         codec_config_.sample_rate = codec_user_config_.sample_rate;
677       }
678       break;
679     case BTAV_A2DP_CODEC_SAMPLE_RATE_48000:
680       if (sampleRate & A2DP_APTX_HD_SAMPLERATE_48000) {
681         result_config_cie.sampleRate = A2DP_APTX_HD_SAMPLERATE_48000;
682         codec_capability_.sample_rate = codec_user_config_.sample_rate;
683         codec_config_.sample_rate = codec_user_config_.sample_rate;
684       }
685       break;
686     case BTAV_A2DP_CODEC_SAMPLE_RATE_88200:
687     case BTAV_A2DP_CODEC_SAMPLE_RATE_96000:
688     case BTAV_A2DP_CODEC_SAMPLE_RATE_176400:
689     case BTAV_A2DP_CODEC_SAMPLE_RATE_192000:
690     case BTAV_A2DP_CODEC_SAMPLE_RATE_16000:
691     case BTAV_A2DP_CODEC_SAMPLE_RATE_24000:
692     case BTAV_A2DP_CODEC_SAMPLE_RATE_NONE:
693       codec_capability_.sample_rate = BTAV_A2DP_CODEC_SAMPLE_RATE_NONE;
694       codec_config_.sample_rate = BTAV_A2DP_CODEC_SAMPLE_RATE_NONE;
695       break;
696   }
697 
698   // Select the sample frequency if there is no user preference
699   do {
700     // Compute the selectable capability
701     if (sampleRate & A2DP_APTX_HD_SAMPLERATE_44100) {
702       codec_selectable_capability_.sample_rate |=
703           BTAV_A2DP_CODEC_SAMPLE_RATE_44100;
704     }
705     if (sampleRate & A2DP_APTX_HD_SAMPLERATE_48000) {
706       codec_selectable_capability_.sample_rate |=
707           BTAV_A2DP_CODEC_SAMPLE_RATE_48000;
708     }
709 
710     if (codec_config_.sample_rate != BTAV_A2DP_CODEC_SAMPLE_RATE_NONE) break;
711 
712     // Compute the common capability
713     if (sampleRate & A2DP_APTX_HD_SAMPLERATE_44100)
714       codec_capability_.sample_rate |= BTAV_A2DP_CODEC_SAMPLE_RATE_44100;
715     if (sampleRate & A2DP_APTX_HD_SAMPLERATE_48000)
716       codec_capability_.sample_rate |= BTAV_A2DP_CODEC_SAMPLE_RATE_48000;
717 
718     // No user preference - try the codec audio config
719     if (select_audio_sample_rate(&codec_audio_config_, sampleRate,
720                                  &result_config_cie, &codec_config_)) {
721       break;
722     }
723 
724     // No user preference - try the default config
725     if (select_best_sample_rate(
726             a2dp_aptx_hd_default_config.sampleRate & peer_info_cie.sampleRate,
727             &result_config_cie, &codec_config_)) {
728       break;
729     }
730 
731     // No user preference - use the best match
732     if (select_best_sample_rate(sampleRate, &result_config_cie,
733                                 &codec_config_)) {
734       break;
735     }
736   } while (false);
737   if (codec_config_.sample_rate == BTAV_A2DP_CODEC_SAMPLE_RATE_NONE) {
738     log::error(
739         "cannot match sample frequency: local caps = 0x{:x} peer info = 0x{:x}",
740         a2dp_aptx_hd_source_caps.sampleRate, peer_info_cie.sampleRate);
741     goto fail;
742   }
743 
744   //
745   // Select the bits per sample
746   //
747   // NOTE: this information is NOT included in the aptX-HD A2DP codec
748   // description that is sent OTA.
749   codec_config_.bits_per_sample = BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE;
750   switch (codec_user_config_.bits_per_sample) {
751     case BTAV_A2DP_CODEC_BITS_PER_SAMPLE_24:
752       codec_capability_.bits_per_sample = codec_user_config_.bits_per_sample;
753       codec_config_.bits_per_sample = codec_user_config_.bits_per_sample;
754       break;
755     case BTAV_A2DP_CODEC_BITS_PER_SAMPLE_16:
756     case BTAV_A2DP_CODEC_BITS_PER_SAMPLE_32:
757     case BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE:
758       codec_capability_.bits_per_sample = BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE;
759       codec_config_.bits_per_sample = BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE;
760       break;
761   }
762 
763   // Select the bits per sample if there is no user preference
764   do {
765     // Compute the selectable capability
766     codec_selectable_capability_.bits_per_sample =
767         a2dp_aptx_hd_source_caps.bits_per_sample;
768 
769     if (codec_config_.bits_per_sample != BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE)
770       break;
771 
772     // Compute the common capability
773     codec_capability_.bits_per_sample = BTAV_A2DP_CODEC_BITS_PER_SAMPLE_24;
774 
775     // No user preference - try the codec audio config
776     if (select_audio_bits_per_sample(&codec_audio_config_, &codec_config_)) {
777       break;
778     }
779 
780     // No user preference - try the default config
781     if (select_best_bits_per_sample(&codec_config_)) {
782       break;
783     }
784 
785     // No user preference - use the best match
786     // NOTE: no-op - kept here for consistency
787     if (select_best_bits_per_sample(&codec_config_)) {
788       break;
789     }
790   } while (false);
791   if (codec_config_.bits_per_sample == BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE) {
792     log::error("cannot match bits per sample: user preference = 0x{:x}",
793                codec_user_config_.bits_per_sample);
794     goto fail;
795   }
796 
797   //
798   // Select the channel mode
799   //
800   channelMode =
801       a2dp_aptx_hd_source_caps.channelMode & peer_info_cie.channelMode;
802   codec_config_.channel_mode = BTAV_A2DP_CODEC_CHANNEL_MODE_NONE;
803   switch (codec_user_config_.channel_mode) {
804     case BTAV_A2DP_CODEC_CHANNEL_MODE_MONO:
805       if (channelMode & A2DP_APTX_HD_CHANNELS_MONO) {
806         result_config_cie.channelMode = A2DP_APTX_HD_CHANNELS_MONO;
807         codec_capability_.channel_mode = codec_user_config_.channel_mode;
808         codec_config_.channel_mode = codec_user_config_.channel_mode;
809       }
810       break;
811     case BTAV_A2DP_CODEC_CHANNEL_MODE_STEREO:
812       if (channelMode & A2DP_APTX_HD_CHANNELS_STEREO) {
813         result_config_cie.channelMode = A2DP_APTX_HD_CHANNELS_STEREO;
814         codec_capability_.channel_mode = codec_user_config_.channel_mode;
815         codec_config_.channel_mode = codec_user_config_.channel_mode;
816       }
817       break;
818     case BTAV_A2DP_CODEC_CHANNEL_MODE_NONE:
819       codec_capability_.channel_mode = BTAV_A2DP_CODEC_CHANNEL_MODE_NONE;
820       codec_config_.channel_mode = BTAV_A2DP_CODEC_CHANNEL_MODE_NONE;
821       break;
822   }
823 
824   // Select the channel mode if there is no user preference
825   do {
826     // Compute the selectable capability
827     if (channelMode & A2DP_APTX_HD_CHANNELS_MONO) {
828       codec_selectable_capability_.channel_mode |=
829           BTAV_A2DP_CODEC_CHANNEL_MODE_MONO;
830     }
831     if (channelMode & A2DP_APTX_HD_CHANNELS_STEREO) {
832       codec_selectable_capability_.channel_mode |=
833           BTAV_A2DP_CODEC_CHANNEL_MODE_STEREO;
834     }
835 
836     if (codec_config_.channel_mode != BTAV_A2DP_CODEC_CHANNEL_MODE_NONE) break;
837 
838     // Compute the common capability
839     if (channelMode & A2DP_APTX_HD_CHANNELS_MONO)
840       codec_capability_.channel_mode |= BTAV_A2DP_CODEC_CHANNEL_MODE_MONO;
841     if (channelMode & A2DP_APTX_HD_CHANNELS_STEREO)
842       codec_capability_.channel_mode |= BTAV_A2DP_CODEC_CHANNEL_MODE_STEREO;
843 
844     // No user preference - try the codec audio config
845     if (select_audio_channel_mode(&codec_audio_config_, channelMode,
846                                   &result_config_cie, &codec_config_)) {
847       break;
848     }
849 
850     // No user preference - try the default config
851     if (select_best_channel_mode(
852             a2dp_aptx_hd_default_config.channelMode & peer_info_cie.channelMode,
853             &result_config_cie, &codec_config_)) {
854       break;
855     }
856 
857     // No user preference - use the best match
858     if (select_best_channel_mode(channelMode, &result_config_cie,
859                                  &codec_config_)) {
860       break;
861     }
862   } while (false);
863   if (codec_config_.channel_mode == BTAV_A2DP_CODEC_CHANNEL_MODE_NONE) {
864     log::error(
865         "cannot match channel mode: local caps = 0x{:x} peer info = 0x{:x}",
866         a2dp_aptx_hd_source_caps.channelMode, peer_info_cie.channelMode);
867     goto fail;
868   }
869 
870   //
871   // Set the rest of the fields as bit-wise AND operation
872   //
873   result_config_cie.acl_sprint_reserved0 =
874       a2dp_aptx_hd_source_caps.acl_sprint_reserved0 &
875       peer_info_cie.acl_sprint_reserved0;
876   result_config_cie.acl_sprint_reserved1 =
877       a2dp_aptx_hd_source_caps.acl_sprint_reserved1 &
878       peer_info_cie.acl_sprint_reserved1;
879   result_config_cie.acl_sprint_reserved2 =
880       a2dp_aptx_hd_source_caps.acl_sprint_reserved2 &
881       peer_info_cie.acl_sprint_reserved2;
882   result_config_cie.acl_sprint_reserved3 =
883       a2dp_aptx_hd_source_caps.acl_sprint_reserved3 &
884       peer_info_cie.acl_sprint_reserved3;
885 
886   if (A2DP_BuildInfoAptxHd(AVDT_MEDIA_TYPE_AUDIO, &result_config_cie,
887                            p_result_codec_config) != A2DP_SUCCESS) {
888     goto fail;
889   }
890 
891   //
892   // Copy the codec-specific fields if they are not zero
893   //
894   if (codec_user_config_.codec_specific_1 != 0)
895     codec_config_.codec_specific_1 = codec_user_config_.codec_specific_1;
896   if (codec_user_config_.codec_specific_2 != 0)
897     codec_config_.codec_specific_2 = codec_user_config_.codec_specific_2;
898   if (codec_user_config_.codec_specific_3 != 0)
899     codec_config_.codec_specific_3 = codec_user_config_.codec_specific_3;
900   if (codec_user_config_.codec_specific_4 != 0)
901     codec_config_.codec_specific_4 = codec_user_config_.codec_specific_4;
902 
903   // Create a local copy of the peer codec capability/config, and the
904   // result codec config.
905   if (is_capability) {
906     status = A2DP_BuildInfoAptxHd(AVDT_MEDIA_TYPE_AUDIO, &peer_info_cie,
907                                   ota_codec_peer_capability_);
908   } else {
909     status = A2DP_BuildInfoAptxHd(AVDT_MEDIA_TYPE_AUDIO, &peer_info_cie,
910                                   ota_codec_peer_config_);
911   }
912   log::assert_that(status == A2DP_SUCCESS,
913                    "assert failed: status == A2DP_SUCCESS");
914   status = A2DP_BuildInfoAptxHd(AVDT_MEDIA_TYPE_AUDIO, &result_config_cie,
915                                 ota_codec_config_);
916   log::assert_that(status == A2DP_SUCCESS,
917                    "assert failed: status == A2DP_SUCCESS");
918   return true;
919 
920 fail:
921   // Restore the internal state
922   codec_config_ = saved_codec_config;
923   codec_capability_ = saved_codec_capability;
924   codec_selectable_capability_ = saved_codec_selectable_capability;
925   codec_user_config_ = saved_codec_user_config;
926   codec_audio_config_ = saved_codec_audio_config;
927   memcpy(ota_codec_config_, saved_ota_codec_config, sizeof(ota_codec_config_));
928   memcpy(ota_codec_peer_capability_, saved_ota_codec_peer_capability,
929          sizeof(ota_codec_peer_capability_));
930   memcpy(ota_codec_peer_config_, saved_ota_codec_peer_config,
931          sizeof(ota_codec_peer_config_));
932   return false;
933 }
934 
setPeerCodecCapabilities(const uint8_t * p_peer_codec_capabilities)935 bool A2dpCodecConfigAptxHd::setPeerCodecCapabilities(
936     const uint8_t* p_peer_codec_capabilities) {
937   std::lock_guard<std::recursive_mutex> lock(codec_mutex_);
938   tA2DP_APTX_HD_CIE peer_info_cie;
939   uint8_t sampleRate;
940   uint8_t channelMode;
941 
942   // Save the internal state
943   btav_a2dp_codec_config_t saved_codec_selectable_capability =
944       codec_selectable_capability_;
945   uint8_t saved_ota_codec_peer_capability[AVDT_CODEC_SIZE];
946   memcpy(saved_ota_codec_peer_capability, ota_codec_peer_capability_,
947          sizeof(ota_codec_peer_capability_));
948 
949   tA2DP_STATUS status =
950       A2DP_ParseInfoAptxHd(&peer_info_cie, p_peer_codec_capabilities, true);
951   if (status != A2DP_SUCCESS) {
952     log::error("can't parse peer's capabilities: error = {}", status);
953     goto fail;
954   }
955 
956   // Compute the selectable capability - sample rate
957   sampleRate = a2dp_aptx_hd_source_caps.sampleRate & peer_info_cie.sampleRate;
958   if (sampleRate & A2DP_APTX_HD_SAMPLERATE_44100) {
959     codec_selectable_capability_.sample_rate |=
960         BTAV_A2DP_CODEC_SAMPLE_RATE_44100;
961   }
962   if (sampleRate & A2DP_APTX_HD_SAMPLERATE_48000) {
963     codec_selectable_capability_.sample_rate |=
964         BTAV_A2DP_CODEC_SAMPLE_RATE_48000;
965   }
966 
967   // Compute the selectable capability - bits per sample
968   codec_selectable_capability_.bits_per_sample =
969       a2dp_aptx_hd_source_caps.bits_per_sample;
970 
971   // Compute the selectable capability - channel mode
972   channelMode =
973       a2dp_aptx_hd_source_caps.channelMode & peer_info_cie.channelMode;
974   if (channelMode & A2DP_APTX_HD_CHANNELS_MONO) {
975     codec_selectable_capability_.channel_mode |=
976         BTAV_A2DP_CODEC_CHANNEL_MODE_MONO;
977   }
978   if (channelMode & A2DP_APTX_HD_CHANNELS_STEREO) {
979     codec_selectable_capability_.channel_mode |=
980         BTAV_A2DP_CODEC_CHANNEL_MODE_STEREO;
981   }
982 
983   status = A2DP_BuildInfoAptxHd(AVDT_MEDIA_TYPE_AUDIO, &peer_info_cie,
984                                 ota_codec_peer_capability_);
985   log::assert_that(status == A2DP_SUCCESS,
986                    "assert failed: status == A2DP_SUCCESS");
987   return true;
988 
989 fail:
990   // Restore the internal state
991   codec_selectable_capability_ = saved_codec_selectable_capability;
992   memcpy(ota_codec_peer_capability_, saved_ota_codec_peer_capability,
993          sizeof(ota_codec_peer_capability_));
994   return false;
995 }
996