Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 0f6124bc authored by Cheney Ni's avatar Cheney Ni
Browse files

Fallback to the legacy HAL when IBluetoothAudioProvidersFactory is unsupported

Because the stack may run without the new BluetoothAudio HAL like GSI
under old devices, it will be nullptr to getService from the
IBluetoothAudioProvidersFactory in such condition. We take nullptr as
unsupported, and fallback to the legacy HAL.

Bug: 128419724
Test: Manually running A2DP and hearing aid with / without the HAL
Change-Id: I606abc3e5b63b7857c3307c879fd4cbe46dd05d9
parent 5cbf0658
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -46,6 +46,7 @@ cc_test {
        "libcutils",
        "libfmq",
        "libhidlbase",
        "libhidltransport",
        "liblog",
        "libutils",
    ],
+21 −12
Original line number Diff line number Diff line
@@ -209,7 +209,7 @@ auto session_type = SessionType::UNKNOWN;
// initialized
uint16_t remote_delay = 0;

bool btaudio_a2dp_supported = false;
bool btaudio_a2dp_disabled = false;
bool is_configured = false;

BluetoothAudioCtrlAck a2dp_ack_to_bt_audio_ctrl_ack(tA2DP_CTRL_ACK ack) {
@@ -543,21 +543,21 @@ bool a2dp_get_selected_hal_pcm_config(PcmParameters* pcm_config) {
          pcm_config->channelMode != ChannelMode::UNKNOWN);
}

}  // namespace

namespace bluetooth {
namespace audio {
namespace a2dp {

// Checking if new bluetooth_audio is supported
bool is_hal_2_0_supported() {
bool is_hal_2_0_force_disabled() {
  if (!is_configured) {
    btaudio_a2dp_supported = !osi_property_get_bool(BLUETOOTH_AUDIO_HAL_PROP_DISABLED, false);
    btaudio_a2dp_disabled = osi_property_get_bool(BLUETOOTH_AUDIO_HAL_PROP_DISABLED, false);
    is_configured = true;
  }
  return btaudio_a2dp_supported;
  return btaudio_a2dp_disabled;
}

}  // namespace

namespace bluetooth {
namespace audio {
namespace a2dp {

// Checking if new bluetooth_audio is enabled
bool is_hal_2_0_enabled() { return a2dp_hal_clientif != nullptr; }

@@ -565,8 +565,8 @@ bool is_hal_2_0_enabled() { return a2dp_hal_clientif != nullptr; }
bool init(bluetooth::common::MessageLoopThread* message_loop) {
  LOG(INFO) << __func__;

  if (!is_hal_2_0_supported()) {
    LOG(ERROR) << __func__ << ": BluetoothAudio HAL is not supported";
  if (is_hal_2_0_force_disabled()) {
    LOG(ERROR) << __func__ << ": BluetoothAudio HAL is disabled";
    return false;
  }

@@ -578,6 +578,15 @@ bool init(bluetooth::common::MessageLoopThread* message_loop) {
  a2dp_sink = new A2dpTransport(session_type);
  a2dp_hal_clientif = new bluetooth::audio::BluetoothAudioClientInterface(
      a2dp_sink, message_loop);
  if (!a2dp_hal_clientif->IsValid()) {
    LOG(WARNING) << __func__ << ": BluetoothAudio HAL for A2DP session=" << toString(session_type) << " is invalid?!";
    delete a2dp_hal_clientif;
    a2dp_hal_clientif = nullptr;
    delete a2dp_sink;
    a2dp_sink = nullptr;
    return false;
  }

  if (remote_delay != 0) {
    LOG(INFO) << __func__ << ": restore DELAY "
              << static_cast<float>(remote_delay / 10.0) << " ms";
+0 −2
Original line number Diff line number Diff line
@@ -23,8 +23,6 @@ namespace bluetooth {
namespace audio {
namespace a2dp {

bool is_hal_2_0_supported();

// Check if new bluetooth_audio is enabled
bool is_hal_2_0_enabled();

+24 −8
Original line number Diff line number Diff line
@@ -20,8 +20,10 @@

#include <android/hardware/bluetooth/audio/2.0/IBluetoothAudioPort.h>
#include <android/hardware/bluetooth/audio/2.0/IBluetoothAudioProvidersFactory.h>
#include <android/hidl/manager/1.2/IServiceManager.h>
#include <base/logging.h>
#include <hidl/MQDescriptor.h>
#include <hidl/ServiceManagement.h>
#include <future>

#include "osi/include/log.h"
@@ -41,6 +43,8 @@ using DataMQ = ::android::hardware::MessageQueue<

static constexpr int kDefaultDataReadTimeoutMs = 10;      // 10 ms
static constexpr int kDefaultDataReadPollIntervalMs = 1;  // non-blocking poll
static constexpr char kFullyQualifiedInterfaceName[] =
    "android.hardware.bluetooth.audio@2.0::IBluetoothAudioProvidersFactory";

std::ostream& operator<<(std::ostream& os, const BluetoothAudioCtrlAck& ack) {
  switch (ack) {
@@ -186,14 +190,26 @@ class BluetoothAudioDeathRecipient
  }
};

BluetoothAudioClientInterface::BluetoothAudioClientInterface(
    IBluetoothTransportInstance* sink,
BluetoothAudioClientInterface::BluetoothAudioClientInterface(IBluetoothTransportInstance* sink,
                                                             bluetooth::common::MessageLoopThread* message_loop)
    : sink_(sink),
      session_started_(false),
      mDataMQ(nullptr),
    : sink_(sink), provider_(nullptr), session_started_(false), mDataMQ(nullptr),
      death_recipient_(new BluetoothAudioDeathRecipient(this, message_loop)) {
  auto service_manager = android::hardware::defaultServiceManager1_2();
  CHECK(service_manager != nullptr);
  size_t instance_count = 0;
  auto listManifestByInterface_cb = [&instance_count](const hidl_vec<android::hardware::hidl_string>& instanceNames) {
    instance_count = instanceNames.size();
    LOG(INFO) << "listManifestByInterface_cb returns " << instance_count << " instance(s)";
  };
  auto hidl_retval = service_manager->listManifestByInterface(kFullyQualifiedInterfaceName, listManifestByInterface_cb);
  if (!hidl_retval.isOk()) {
    LOG(FATAL) << __func__ << ": IServiceManager::listByInterface failure: " << hidl_retval.description();
  }
  if (instance_count > 0) {
    fetch_audio_provider();
  } else {
    LOG(WARNING) << "IBluetoothAudioProvidersFactory not declared";
  }
}

BluetoothAudioClientInterface::~BluetoothAudioClientInterface() {
@@ -217,7 +233,7 @@ void BluetoothAudioClientInterface::fetch_audio_provider() {

  android::sp<IBluetoothAudioProvidersFactory> providersFactory =
      IBluetoothAudioProvidersFactory::getService();
  CHECK(providersFactory != nullptr);
  CHECK(providersFactory != nullptr) << "IBluetoothAudioProvidersFactory::getService() failed";
  LOG(INFO) << "IBluetoothAudioProvidersFactory::getService() returned "
            << providersFactory.get()
            << (providersFactory->isRemote() ? " (remote)" : " (local)");
+4 −0
Original line number Diff line number Diff line
@@ -131,6 +131,10 @@ class BluetoothAudioClientInterface {

  ~BluetoothAudioClientInterface();

  bool IsValid() const {
    return provider_ != nullptr;
  }

  std::vector<AudioCapabilities> GetAudioCapabilities() const;

  bool UpdateAudioConfig(const AudioConfiguration& audioConfig);
Loading