From feeaf5f8cf31394d6f737543f1d0572ca91d487c Mon Sep 17 00:00:00 2001 From: Jack He Date: Fri, 8 Jun 2018 20:13:23 -0700 Subject: [PATCH] Multi-A2DP: Fix timing and codec measurement in metrics * Copy BtifMediaStats and SchedulingStats when updating metrics to avoid race conditions * Do not log audio_duration_ms if session_end_us <= session_start_us * Clear cached A2DP metrics when LogBluetoothSessionEnd() is called * Log codec information along-side A2DP metrics * Log whether A2DP offload is enabled along-side A2DP metrics Multi-A2DP: * Log LogBluetoothSessionStart at btif_a2dp_source_start_session_delayed * Log LogBluetoothSessionEnd at btif_a2dp_source_end_session_delayed Unit Test: * Wrote A2DPSessionTwoUpdatesSeparatedbyEndTest that will fail if A2DP metrics are not cleared when LogBluetoothSessionEnd is called Bug: 109953464 Test: make, net_test_osi::BluetoothMetricsLoggerTest, net_test_osi::BluetoothA2DPSessionMetricsTest Change-Id: I6a311dce8035ce2e3f39773c260ea9eaef73e45b --- btif/src/btif_a2dp_source.cc | 56 ++++++++------ osi/include/metrics.h | 2 + osi/src/metrics.cc | 34 ++++++++- osi/test/metrics_test.cc | 131 ++++++++++++++++++++++++++++++-- proto/bluetooth/metrics/bluetooth.proto | 15 ++++ 5 files changed, 209 insertions(+), 29 deletions(-) diff --git a/btif/src/btif_a2dp_source.cc b/btif/src/btif_a2dp_source.cc index 2a4ec8f04..c4b3006e0 100644 --- a/btif/src/btif_a2dp_source.cc +++ b/btif/src/btif_a2dp_source.cc @@ -132,6 +132,7 @@ class BtifMediaStats { media_read_total_underflow_bytes = 0; media_read_total_underflow_count = 0; media_read_last_underflow_us = 0; + codec_index = -1; } uint64_t session_start_us; @@ -160,6 +161,8 @@ class BtifMediaStats { size_t media_read_total_underflow_bytes; size_t media_read_total_underflow_count; uint64_t media_read_last_underflow_us; + + int codec_index = -1; }; class BtWorkerThread { @@ -380,6 +383,7 @@ void btif_a2dp_source_accumulate_stats(BtifMediaStats* src, dst->media_read_total_underflow_count += src->media_read_total_underflow_count; dst->media_read_last_underflow_us = src->media_read_last_underflow_us; + if (dst->codec_index < 0) dst->codec_index = src->codec_index; btif_a2dp_source_accumulate_scheduling_stats(&src->tx_queue_enqueue_stats, &dst->tx_queue_enqueue_stats); btif_a2dp_source_accumulate_scheduling_stats(&src->tx_queue_dequeue_stats, @@ -427,8 +431,6 @@ static void btif_a2dp_source_startup_delayed(void) { raise_priority_a2dp(TASK_HIGH_MEDIA); btif_a2dp_control_init(); btif_a2dp_source_cb.SetState(BtifA2dpSource::kStateRunning); - BluetoothMetricsLogger::GetInstance()->LogBluetoothSessionStart( - system_bt_osi::CONNECTION_TECHNOLOGY_TYPE_BREDR, 0); } bool btif_a2dp_source_start_session(const RawAddress& peer_address) { @@ -452,6 +454,8 @@ static void btif_a2dp_source_start_session_delayed( if (btif_av_is_a2dp_offload_enabled()) { btif_a2dp_audio_interface_start_session(); } + BluetoothMetricsLogger::GetInstance()->LogBluetoothSessionStart( + system_bt_osi::CONNECTION_TECHNOLOGY_TYPE_BREDR, 0); } bool btif_a2dp_source_restart_session(const RawAddress& old_peer_address, @@ -499,6 +503,8 @@ static void btif_a2dp_source_end_session_delayed( const RawAddress& peer_address) { LOG_INFO(LOG_TAG, "%s: peer_address=%s", __func__, peer_address.ToString().c_str()); + BluetoothMetricsLogger::GetInstance()->LogBluetoothSessionEnd( + system_bt_osi::DISCONNECT_REASON_UNKNOWN, 0); if (btif_a2dp_source_cb.State() != BtifA2dpSource::kStateRunning) { LOG_ERROR(LOG_TAG, "%s: A2DP Source media task is not running", __func__); return; @@ -538,8 +544,6 @@ static void btif_a2dp_source_shutdown_delayed(void) { btif_a2dp_source_cb.tx_audio_queue = nullptr; btif_a2dp_source_cb.SetState(BtifA2dpSource::kStateOff); - BluetoothMetricsLogger::GetInstance()->LogBluetoothSessionEnd( - system_bt_osi::DISCONNECT_REASON_UNKNOWN, 0); } void btif_a2dp_source_cleanup(void) { @@ -627,14 +631,6 @@ void btif_a2dp_source_start_audio_req(void) { btif_a2dp_source_thread.DoInThread( FROM_HERE, base::Bind(&btif_a2dp_source_audio_tx_start_event)); - btif_a2dp_source_cb.stats.Reset(); - // Assign session_start_us to 1 when time_get_os_boottime_us() is 0 to - // indicate btif_a2dp_source_start_audio_req() has been called - btif_a2dp_source_cb.stats.session_start_us = time_get_os_boottime_us(); - if (btif_a2dp_source_cb.stats.session_start_us == 0) { - btif_a2dp_source_cb.stats.session_start_us = 1; - } - btif_a2dp_source_cb.stats.session_end_us = 0; } void btif_a2dp_source_stop_audio_req(void) { @@ -642,11 +638,6 @@ void btif_a2dp_source_stop_audio_req(void) { btif_a2dp_source_thread.DoInThread( FROM_HERE, base::Bind(&btif_a2dp_source_audio_tx_stop_event)); - - btif_a2dp_source_cb.stats.session_end_us = time_get_os_boottime_us(); - btif_a2dp_source_update_metrics(); - btif_a2dp_source_accumulate_stats(&btif_a2dp_source_cb.stats, - &btif_a2dp_source_cb.accumulated_stats); } void btif_a2dp_source_encoder_user_config_update_req( @@ -777,15 +768,32 @@ static void btif_a2dp_source_audio_tx_start_event(void) { alarm_set(btif_a2dp_source_cb.media_alarm, btif_a2dp_source_cb.encoder_interface->get_encoder_interval_ms(), btif_a2dp_source_alarm_cb, nullptr); + + btif_a2dp_source_cb.stats.Reset(); + // Assign session_start_us to 1 when time_get_os_boottime_us() is 0 to + // indicate btif_a2dp_source_start_audio_req() has been called + btif_a2dp_source_cb.stats.session_start_us = time_get_os_boottime_us(); + if (btif_a2dp_source_cb.stats.session_start_us == 0) { + btif_a2dp_source_cb.stats.session_start_us = 1; + } + btif_a2dp_source_cb.stats.session_end_us = 0; + A2dpCodecConfig* codec_config = bta_av_get_a2dp_current_codec(); + if (codec_config != nullptr) { + btif_a2dp_source_cb.stats.codec_index = codec_config->codecIndex(); + } } static void btif_a2dp_source_audio_tx_stop_event(void) { LOG_INFO(LOG_TAG, "%s: media_alarm is %srunning, streaming %s", __func__, alarm_is_scheduled(btif_a2dp_source_cb.media_alarm) ? "" : "not ", btif_a2dp_source_is_streaming() ? "true" : "false"); - if (btif_av_is_a2dp_offload_enabled()) return; + btif_a2dp_source_cb.stats.session_end_us = time_get_os_boottime_us(); + btif_a2dp_source_update_metrics(); + btif_a2dp_source_accumulate_stats(&btif_a2dp_source_cb.stats, + &btif_a2dp_source_cb.accumulated_stats); + uint8_t p_buf[AUDIO_STREAM_OUTPUT_BUFFER_SZ * 2]; uint16_t event; @@ -1212,17 +1220,21 @@ void btif_a2dp_source_debug_dump(int fd) { } static void btif_a2dp_source_update_metrics(void) { - const BtifMediaStats& stats = btif_a2dp_source_cb.stats; - const SchedulingStats& enqueue_stats = stats.tx_queue_enqueue_stats; + BtifMediaStats stats = btif_a2dp_source_cb.stats; + SchedulingStats enqueue_stats = stats.tx_queue_enqueue_stats; A2dpSessionMetrics metrics; + metrics.codec_index = stats.codec_index; + metrics.is_a2dp_offload = btif_av_is_a2dp_offload_enabled(); // session_start_us is 0 when btif_a2dp_source_start_audio_req() is not called // mark the metric duration as invalid (-1) in this case if (stats.session_start_us != 0) { int64_t session_end_us = stats.session_end_us == 0 ? time_get_os_boottime_us() : stats.session_end_us; - metrics.audio_duration_ms = - (session_end_us - stats.session_start_us) / 1000; + if (static_cast(session_end_us) > stats.session_start_us) { + metrics.audio_duration_ms = + (session_end_us - stats.session_start_us) / 1000; + } } if (enqueue_stats.total_updates > 1) { diff --git a/osi/include/metrics.h b/osi/include/metrics.h index 4f968d2d7..504a16a5a 100644 --- a/osi/include/metrics.h +++ b/osi/include/metrics.h @@ -105,6 +105,8 @@ class A2dpSessionMetrics { int32_t buffer_overruns_total = -1; float buffer_underruns_average = -1; int32_t buffer_underruns_count = -1; + int64_t codec_index = -1; + bool is_a2dp_offload = false; }; class BluetoothMetricsLogger { diff --git a/osi/src/metrics.cc b/osi/src/metrics.cc index 96907c0b5..73450b944 100644 --- a/osi/src/metrics.cc +++ b/osi/src/metrics.cc @@ -29,6 +29,7 @@ #include #include +#include #include "bluetooth/metrics/bluetooth.pb.h" #include "osi/include/leaky_bonded_queue.h" @@ -42,6 +43,7 @@ namespace system_bt_osi { using bluetooth::metrics::BluetoothMetricsProto::A2DPSession; +using bluetooth::metrics::BluetoothMetricsProto::A2dpSourceCodec; using bluetooth::metrics::BluetoothMetricsProto::BluetoothLog; using bluetooth::metrics::BluetoothMetricsProto::BluetoothSession; using bluetooth::metrics::BluetoothMetricsProto:: @@ -140,6 +142,12 @@ void A2dpSessionMetrics::Update(const A2dpSessionMetrics& metrics) { buffer_underruns_count += metrics.buffer_underruns_count; } } + if (codec_index < 0) { + codec_index = metrics.codec_index; + } + if (!is_a2dp_offload) { + is_a2dp_offload = metrics.is_a2dp_offload; + } } bool A2dpSessionMetrics::operator==(const A2dpSessionMetrics& rhs) const { @@ -151,7 +159,9 @@ bool A2dpSessionMetrics::operator==(const A2dpSessionMetrics& rhs) const { buffer_overruns_max_count == rhs.buffer_overruns_max_count && buffer_overruns_total == rhs.buffer_overruns_total && buffer_underruns_average == rhs.buffer_underruns_average && - buffer_underruns_count == rhs.buffer_underruns_count; + buffer_underruns_count == rhs.buffer_underruns_count && + codec_index == rhs.codec_index && + is_a2dp_offload == rhs.is_a2dp_offload; } static DeviceInfo_DeviceType get_device_type(device_type_t type) { @@ -230,6 +240,23 @@ static BluetoothSession_DisconnectReasonType get_disconnect_reason_type( } } +static A2dpSourceCodec get_a2dp_source_codec(int64_t codec_index) { + switch (codec_index) { + case BTAV_A2DP_CODEC_INDEX_SOURCE_SBC: + return A2dpSourceCodec::A2DP_SOURCE_CODEC_SBC; + case BTAV_A2DP_CODEC_INDEX_SOURCE_AAC: + return A2dpSourceCodec::A2DP_SOURCE_CODEC_AAC; + case BTAV_A2DP_CODEC_INDEX_SOURCE_APTX: + return A2dpSourceCodec::A2DP_SOURCE_CODEC_APTX; + case BTAV_A2DP_CODEC_INDEX_SOURCE_APTX_HD: + return A2dpSourceCodec::A2DP_SOURCE_CODEC_APTX_HD; + case BTAV_A2DP_CODEC_INDEX_SOURCE_LDAC: + return A2dpSourceCodec::A2DP_SOURCE_CODEC_LDAC; + default: + return A2dpSourceCodec::A2DP_SOURCE_CODEC_UNKNOWN; + } +} + struct BluetoothMetricsLogger::impl { impl(size_t max_bluetooth_session, size_t max_pair_event, size_t max_wake_event, size_t max_scan_event) @@ -356,6 +383,7 @@ void BluetoothMetricsLogger::LogBluetoothSessionEnd( get_disconnect_reason_type(disconnect_reason)); pimpl_->bt_session_queue_->Enqueue(pimpl_->bluetooth_session_); pimpl_->bluetooth_session_ = nullptr; + pimpl_->a2dp_session_metrics_ = A2dpSessionMetrics(); { std::lock_guard log_lock(pimpl_->bluetooth_log_lock_); pimpl_->bluetooth_log_->set_num_bluetooth_session( @@ -404,6 +432,10 @@ void BluetoothMetricsLogger::LogA2dpSession( pimpl_->a2dp_session_metrics_.buffer_underruns_average); a2dp_session->set_buffer_underruns_count( pimpl_->a2dp_session_metrics_.buffer_underruns_count); + a2dp_session->set_source_codec( + get_a2dp_source_codec(pimpl_->a2dp_session_metrics_.codec_index)); + a2dp_session->set_is_a2dp_offload( + pimpl_->a2dp_session_metrics_.is_a2dp_offload); } void BluetoothMetricsLogger::LogHeadsetProfileRfcConnection( diff --git a/osi/test/metrics_test.cc b/osi/test/metrics_test.cc index 2c9762f5b..bfb548f63 100644 --- a/osi/test/metrics_test.cc +++ b/osi/test/metrics_test.cc @@ -25,6 +25,7 @@ #include #include +#include #include "bluetooth/metrics/bluetooth.pb.h" #include "osi/include/metrics.h" @@ -35,6 +36,7 @@ namespace testing { using bluetooth::metrics::BluetoothMetricsProto::A2DPSession; +using bluetooth::metrics::BluetoothMetricsProto::A2dpSourceCodec; using bluetooth::metrics::BluetoothMetricsProto::BluetoothLog; using bluetooth::metrics::BluetoothMetricsProto::BluetoothSession; using bluetooth::metrics::BluetoothMetricsProto:: @@ -111,7 +113,8 @@ ScanEvent* MakeScanEvent(ScanEvent_ScanEventType event_type, return event; } -A2DPSession* MakeA2DPSession(const A2dpSessionMetrics& metrics) { +A2DPSession* MakeA2DPSession(const A2dpSessionMetrics& metrics, + A2dpSourceCodec source_codec) { A2DPSession* session = new A2DPSession(); session->set_media_timer_min_millis(metrics.media_timer_min_ms); session->set_media_timer_max_millis(metrics.media_timer_max_ms); @@ -121,6 +124,8 @@ A2DPSession* MakeA2DPSession(const A2dpSessionMetrics& metrics) { session->set_buffer_underruns_average(metrics.buffer_underruns_average); session->set_buffer_underruns_count(metrics.buffer_underruns_count); session->set_audio_duration_millis(metrics.audio_duration_ms); + session->set_source_codec(source_codec); + session->set_is_a2dp_offload(metrics.is_a2dp_offload); return session; } @@ -187,6 +192,8 @@ void GenerateWakeEvents(size_t start, size_t end, FloatNear((b).buffer_underruns_average, 0.01)); \ (a).buffer_underruns_average = (b).buffer_underruns_average; \ EXPECT_EQ((a).buffer_underruns_count, (b).buffer_underruns_count); \ + EXPECT_EQ((a).codec_index, (b).codec_index); \ + EXPECT_EQ((a).is_a2dp_offload, (b).is_a2dp_offload); \ } while (0) /* @@ -220,6 +227,12 @@ TEST(BluetoothA2DPSessionMetricsTest, TestUpdateNormal) { metrics2.buffer_underruns_count = 2400; metrics_sum.buffer_underruns_average = 113.33333333; metrics_sum.buffer_underruns_count = 3600; + metrics1.codec_index = -1; + metrics2.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_AAC; + metrics_sum.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_AAC; + metrics1.is_a2dp_offload = false; + metrics2.is_a2dp_offload = true; + metrics_sum.is_a2dp_offload = true; metrics1.Update(metrics2); COMPARE_A2DP_METRICS(metrics1, metrics_sum); EXPECT_TRUE(metrics1 == metrics_sum); @@ -246,6 +259,10 @@ TEST(BluetoothA2DPSessionMetricsTest, TestUpdateNew) { metrics2.buffer_underruns_count = 2400; metrics_sum.buffer_underruns_average = 130; metrics_sum.buffer_underruns_count = 2400; + metrics2.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_APTX; + metrics_sum.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_APTX; + metrics2.is_a2dp_offload = true; + metrics_sum.is_a2dp_offload = true; metrics1.Update(metrics2); COMPARE_A2DP_METRICS(metrics1, metrics_sum); EXPECT_TRUE(metrics1 == metrics_sum); @@ -272,6 +289,10 @@ TEST(BluetoothA2DPSessionMetricsTest, TestNullUpdate) { metrics2.buffer_underruns_count = 2400; metrics_sum.buffer_underruns_average = 130; metrics_sum.buffer_underruns_count = 2400; + metrics2.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_APTX_HD; + metrics_sum.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_APTX_HD; + metrics2.is_a2dp_offload = true; + metrics_sum.is_a2dp_offload = true; metrics2.Update(metrics1); COMPARE_A2DP_METRICS(metrics2, metrics_sum); EXPECT_TRUE(metrics2 == metrics_sum); @@ -560,10 +581,17 @@ TEST_F(BluetoothMetricsLoggerTest, A2DPSessionTwoUpdatesTest) { metrics2.buffer_underruns_count = 2400; metrics_sum.buffer_underruns_average = 113.33333333; metrics_sum.buffer_underruns_count = 3600; + metrics1.codec_index = -1; + metrics2.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_AAC; + metrics_sum.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_AAC; + metrics1.is_a2dp_offload = false; + metrics2.is_a2dp_offload = true; + metrics_sum.is_a2dp_offload = true; DeviceInfo* info = MakeDeviceInfo( BTM_COD_MAJOR_AUDIO_TEST, DeviceInfo_DeviceType::DeviceInfo_DeviceType_DEVICE_TYPE_BREDR); - A2DPSession* session = MakeA2DPSession(metrics_sum); + A2DPSession* session = + MakeA2DPSession(metrics_sum, A2dpSourceCodec::A2DP_SOURCE_CODEC_AAC); bt_sessions_.push_back(MakeBluetoothSession( 10, BluetoothSession_ConnectionTechnologyType:: @@ -618,10 +646,13 @@ TEST_F(BluetoothMetricsLoggerTest, A2DPSessionTwoUpdatesSeparatedbyDumpTest) { metrics1.buffer_underruns_count = 1200; metrics2.buffer_underruns_average = 130; metrics2.buffer_underruns_count = 2400; + metrics1.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_SBC; + metrics2.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_AAC; DeviceInfo* info = MakeDeviceInfo( BTM_COD_MAJOR_AUDIO_TEST, DeviceInfo_DeviceType::DeviceInfo_DeviceType_DEVICE_TYPE_BREDR); - A2DPSession* session = MakeA2DPSession(metrics1); + A2DPSession* session = + MakeA2DPSession(metrics1, A2dpSourceCodec::A2DP_SOURCE_CODEC_SBC); bt_sessions_.push_back(MakeBluetoothSession( 1, BluetoothSession_ConnectionTechnologyType:: @@ -643,7 +674,7 @@ TEST_F(BluetoothMetricsLoggerTest, A2DPSessionTwoUpdatesSeparatedbyDumpTest) { info = MakeDeviceInfo( BTM_COD_MAJOR_AUDIO_TEST, DeviceInfo_DeviceType::DeviceInfo_DeviceType_DEVICE_TYPE_BREDR); - session = MakeA2DPSession(metrics2); + session = MakeA2DPSession(metrics2, A2dpSourceCodec::A2DP_SOURCE_CODEC_AAC); bt_sessions_.push_back(MakeBluetoothSession( 1, BluetoothSession_ConnectionTechnologyType:: @@ -662,6 +693,86 @@ TEST_F(BluetoothMetricsLoggerTest, A2DPSessionTwoUpdatesSeparatedbyDumpTest) { } /* + * Test Case: A2DPSessionTwoUpdatesSeparatedbyEndTest + * + * 1. Create Instance + * 2. LogBluetoothSessionStart + * 3. LogA2dpSession + * 4. LogBluetoothSessionEnd + * 5. LogBluetoothSessionStart + * 6. LogA2dpSession + * 7. LogBluetoothSessionEnd + * 8. WriteString + * + */ +TEST_F(BluetoothMetricsLoggerTest, A2DPSessionTwoUpdatesSeparatedbyEndTest) { + /* Same metrics from BluetoothA2DPSessionMetricsTest.TestUpdateNormal */ + A2dpSessionMetrics metrics1; + metrics1.audio_duration_ms = 10; + metrics1.media_timer_min_ms = 10; + metrics1.media_timer_max_ms = 100; + metrics1.media_timer_avg_ms = 50; + metrics1.total_scheduling_count = 50; + metrics1.buffer_overruns_max_count = 70; + metrics1.buffer_underruns_average = 80; + metrics1.buffer_underruns_count = 1200; + metrics1.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_SBC; + DeviceInfo* info = MakeDeviceInfo( + BTM_COD_MAJOR_AUDIO_TEST, + DeviceInfo_DeviceType::DeviceInfo_DeviceType_DEVICE_TYPE_BREDR); + A2DPSession* session = + MakeA2DPSession(metrics1, A2dpSourceCodec::A2DP_SOURCE_CODEC_SBC); + bt_sessions_.push_back(MakeBluetoothSession( + 1, + BluetoothSession_ConnectionTechnologyType:: + BluetoothSession_ConnectionTechnologyType_CONNECTION_TECHNOLOGY_TYPE_BREDR, + BluetoothSession_DisconnectReasonType:: + BluetoothSession_DisconnectReasonType_UNKNOWN, + info, nullptr, session)); + UpdateLog(); + BluetoothMetricsLogger::GetInstance()->LogBluetoothSessionStart( + system_bt_osi::CONNECTION_TECHNOLOGY_TYPE_BREDR, 0); + BluetoothMetricsLogger::GetInstance()->LogBluetoothSessionDeviceInfo( + BTM_COD_MAJOR_AUDIO_TEST, system_bt_osi::DEVICE_TYPE_BREDR); + BluetoothMetricsLogger::GetInstance()->LogA2dpSession(metrics1); + sleep_ms(1000); + BluetoothMetricsLogger::GetInstance()->LogBluetoothSessionEnd( + system_bt_osi::DISCONNECT_REASON_UNKNOWN, 0); + std::string msg_str; + BluetoothMetricsLogger::GetInstance()->WriteString(&msg_str); + EXPECT_THAT(msg_str, StrEq(bt_log_str_)); + ClearLog(); + A2dpSessionMetrics metrics2; + metrics2.audio_duration_ms = 25; + metrics2.media_timer_min_ms = 25; + metrics2.media_timer_max_ms = 200; + metrics2.media_timer_avg_ms = 100; + metrics2.total_scheduling_count = 50; + metrics2.buffer_overruns_max_count = 80; + metrics2.buffer_underruns_average = 130; + metrics2.buffer_underruns_count = 2400; + metrics2.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_AAC; + session = MakeA2DPSession(metrics2, A2dpSourceCodec::A2DP_SOURCE_CODEC_AAC); + bt_sessions_.push_back(MakeBluetoothSession( + 1, + BluetoothSession_ConnectionTechnologyType:: + BluetoothSession_ConnectionTechnologyType_CONNECTION_TECHNOLOGY_TYPE_BREDR, + BluetoothSession_DisconnectReasonType:: + BluetoothSession_DisconnectReasonType_UNKNOWN, + nullptr, nullptr, session)); + UpdateLog(); + BluetoothMetricsLogger::GetInstance()->LogBluetoothSessionStart( + system_bt_osi::CONNECTION_TECHNOLOGY_TYPE_BREDR, 0); + sleep_ms(1000); + BluetoothMetricsLogger::GetInstance()->LogA2dpSession(metrics2); + BluetoothMetricsLogger::GetInstance()->LogBluetoothSessionEnd( + system_bt_osi::DISCONNECT_REASON_UNKNOWN, 0); + msg_str.clear(); + BluetoothMetricsLogger::GetInstance()->WriteString(&msg_str); + EXPECT_THAT(msg_str, StrEq(bt_log_str_)); +} + +/* * Test Case 1: A2DPSessionOnlyTest * * 1. Create Instance @@ -700,10 +811,14 @@ TEST_F(BluetoothMetricsLoggerTest, A2DPSessionOnlyTest) { metrics2.buffer_underruns_count = 2400; metrics_sum.buffer_underruns_average = 113.33333333; metrics_sum.buffer_underruns_count = 3600; + metrics1.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_SBC; + metrics2.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_AAC; + metrics_sum.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_SBC; DeviceInfo* info = MakeDeviceInfo( BTM_COD_MAJOR_AUDIO_TEST, DeviceInfo_DeviceType::DeviceInfo_DeviceType_DEVICE_TYPE_BREDR); - A2DPSession* session = MakeA2DPSession(metrics_sum); + A2DPSession* session = + MakeA2DPSession(metrics_sum, A2dpSourceCodec::A2DP_SOURCE_CODEC_SBC); bt_sessions_.push_back(MakeBluetoothSession( 1, BluetoothSession_ConnectionTechnologyType:: @@ -762,6 +877,9 @@ TEST_F(BluetoothMetricsLoggerTest, A2DPSessionDumpBeforeTwoUpdatesTest) { metrics2.buffer_underruns_count = 2400; metrics_sum.buffer_underruns_average = 113.33333333; metrics_sum.buffer_underruns_count = 3600; + metrics1.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_SBC; + metrics2.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_AAC; + metrics_sum.codec_index = BTAV_A2DP_CODEC_INDEX_SOURCE_SBC; DeviceInfo* info = MakeDeviceInfo( BTM_COD_MAJOR_AUDIO_TEST, DeviceInfo_DeviceType::DeviceInfo_DeviceType_DEVICE_TYPE_BREDR); @@ -785,7 +903,8 @@ TEST_F(BluetoothMetricsLoggerTest, A2DPSessionDumpBeforeTwoUpdatesTest) { info = MakeDeviceInfo( BTM_COD_MAJOR_AUDIO_TEST, DeviceInfo_DeviceType::DeviceInfo_DeviceType_DEVICE_TYPE_BREDR); - A2DPSession* session = MakeA2DPSession(metrics_sum); + A2DPSession* session = + MakeA2DPSession(metrics_sum, A2dpSourceCodec::A2DP_SOURCE_CODEC_SBC); bt_sessions_.push_back(MakeBluetoothSession( 1, BluetoothSession_ConnectionTechnologyType:: diff --git a/proto/bluetooth/metrics/bluetooth.proto b/proto/bluetooth/metrics/bluetooth.proto index 67efac5cd..b1e28c3b2 100644 --- a/proto/bluetooth/metrics/bluetooth.proto +++ b/proto/bluetooth/metrics/bluetooth.proto @@ -133,6 +133,15 @@ message RFCommSession { optional int32 tx_bytes = 2; } +enum A2dpSourceCodec { + A2DP_SOURCE_CODEC_UNKNOWN = 0; + A2DP_SOURCE_CODEC_SBC = 1; + A2DP_SOURCE_CODEC_AAC = 2; + A2DP_SOURCE_CODEC_APTX = 3; + A2DP_SOURCE_CODEC_APTX_HD = 4; + A2DP_SOURCE_CODEC_LDAC = 5; +} + // Session information that gets logged for A2DP session. message A2DPSession { // Media timer in milliseconds. @@ -158,6 +167,12 @@ message A2DPSession { // Total audio time in this A2DP session optional int64 audio_duration_millis = 8; + + // Audio codec used in this A2DP session in A2DP source role + optional A2dpSourceCodec source_codec = 9; + + // Whether A2DP offload is enabled in this A2DP session + optional bool is_a2dp_offload = 10; } message PairEvent { -- 2.11.0