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

Commit 5b0b518c authored by William Escande's avatar William Escande
Browse files

Add permission to load library from system_ext

Bluetooth a2dp vendor codec are manage by the presence (or absence) of
the corresponding `.so`. Since we moved as an apex, the `.so` cannot be
found in the current directory.
This CL try to load each `.so` from various location.
This CL add the `/system_ext/${LIB}` to the list of permitted_paths, to
allow dlopen of aptx & aptxHD library.
We ensure we don't load a 32 lib in a 64 module thanks to the
permitted_paths.

Test: build + start bt and watch log
Fix: 223532240
Tag: #refactor
Ignore-AOSP-First: No apex on aosp
Change-Id: Ie1dd9877edc905230a4f6d05b991e26c9908f8c7
parent 069fbbc0
Loading
Loading
Loading
Loading
+9 −0
Original line number Diff line number Diff line
@@ -22,6 +22,9 @@ apex_defaults {
        },
    },

    prebuilts: [
        "bluetooth-linker-config",
    ],
    key: "com.android.bluetooth.key",
    certificate: ":com.android.bluetooth.certificate",
    defaults: ["t-launched-apex-module"],
@@ -33,6 +36,12 @@ apex_defaults {
    compressible: true,
}

linker_config {
    name: "bluetooth-linker-config",
    src: "linker.config.json",
    installable: false,
}

//Mainline bluetooth apex module.
apex {
    name: "com.android.bluetooth",
+5 −0
Original line number Diff line number Diff line
{
    "permittedPaths": [
        "/system_ext/${LIB}"
    ]
}
+22 −0
Original line number Diff line number Diff line
@@ -22,6 +22,8 @@

#include "a2dp_vendor.h"

#include <dlfcn.h>

#include "a2dp_vendor_aptx.h"
#include "a2dp_vendor_aptx_hd.h"
#include "a2dp_vendor_ldac.h"
@@ -660,3 +662,23 @@ std::string A2DP_VendorCodecInfoString(const uint8_t* p_codec_info) {
  return "Unsupported codec vendor_id: " + loghex(vendor_id) +
         " codec_id: " + loghex(codec_id);
}

void* A2DP_VendorCodecLoadExternalLib(const std::vector<std::string>& lib_paths,
                                      const std::string& friendly_name) {
  std::string lib_path_error_list = "";
  for (auto lib_path : lib_paths) {
    void* lib_handle = dlopen(lib_path.c_str(), RTLD_NOW);
    if (lib_handle != NULL) {
      LOG(INFO) << __func__ << "Library found: " << friendly_name << " with ["
                << lib_path << "]."
                << " (Tested libs: " << lib_path_error_list << ")";
      return lib_handle;
    }
    lib_path_error_list += "[ Err: ";
    lib_path_error_list += dlerror();
    lib_path_error_list += " ], ";
  }
  LOG(ERROR) << __func__ << "Failed to open library: " << friendly_name
             << ". (Tested libs: " << lib_path_error_list << ")";
  return nullptr;
}
+14 −5
Original line number Diff line number Diff line
@@ -38,7 +38,8 @@
//
// The aptX encoder shared library, and the functions to use
//
static const char* APTX_ENCODER_LIB_NAME = "libaptX_encoder.so";
static const std::string APTX_ENCODER_LIB_NAME = "libaptX_encoder.so";

static void* aptx_encoder_lib_handle = NULL;

static const char* APTX_ENCODER_INIT_NAME = "aptxbtenc_init";
@@ -111,14 +112,22 @@ static size_t aptx_encode_16bit(tAPTX_FRAMING_PARAMS* framing_params,
                                size_t* data_out_index, uint16_t* data16_in,
                                uint8_t* data_out);

static const std::vector<std::string> APTX_ENCODER_LIB_PATHS = {
    APTX_ENCODER_LIB_NAME,
#ifdef __LP64__
    "/system_ext/lib64/" + APTX_ENCODER_LIB_NAME,
#else
    "/system_ext/lib/" + APTX_ENCODER_LIB_NAME,
#endif
};

bool A2DP_VendorLoadEncoderAptx(void) {
  if (aptx_encoder_lib_handle != NULL) return true;  // Already loaded

  // Open the encoder library
  aptx_encoder_lib_handle = dlopen(APTX_ENCODER_LIB_NAME, RTLD_NOW);
  if (aptx_encoder_lib_handle == NULL) {
    LOG_ERROR("%s: cannot open aptX encoder library %s: %s", __func__,
              APTX_ENCODER_LIB_NAME, dlerror());
  aptx_encoder_lib_handle =
      A2DP_VendorCodecLoadExternalLib(APTX_ENCODER_LIB_PATHS, "aptX encoder");
  if (!aptx_encoder_lib_handle) {
    return false;
  }

+13 −5
Original line number Diff line number Diff line
@@ -38,7 +38,7 @@
//
// The aptX-HD encoder shared library, and the functions to use
//
static const char* APTX_HD_ENCODER_LIB_NAME = "libaptXHD_encoder.so";
static const std::string APTX_HD_ENCODER_LIB_NAME = "libaptXHD_encoder.so";
static void* aptx_hd_encoder_lib_handle = NULL;

static const char* APTX_HD_ENCODER_INIT_NAME = "aptxhdbtenc_init";
@@ -112,14 +112,22 @@ static size_t aptx_hd_encode_24bit(tAPTX_HD_FRAMING_PARAMS* framing_params,
                                   size_t* data_out_index, uint32_t* data32_in,
                                   uint8_t* data_out);

static const std::vector<std::string> APTX_HD_ENCODER_LIB_PATHS = {
    APTX_HD_ENCODER_LIB_NAME,
#ifdef __LP64__
    "/system_ext/lib64/" + APTX_HD_ENCODER_LIB_NAME,
#else
    "/system_ext/lib/" + APTX_HD_ENCODER_LIB_NAME,
#endif
};

bool A2DP_VendorLoadEncoderAptxHd(void) {
  if (aptx_hd_encoder_lib_handle != NULL) return true;  // Already loaded

  // Open the encoder library
  aptx_hd_encoder_lib_handle = dlopen(APTX_HD_ENCODER_LIB_NAME, RTLD_NOW);
  if (aptx_hd_encoder_lib_handle == NULL) {
    LOG_ERROR("%s: cannot open aptX-HD encoder library %s: %s", __func__,
              APTX_HD_ENCODER_LIB_NAME, dlerror());
  aptx_hd_encoder_lib_handle = A2DP_VendorCodecLoadExternalLib(
      APTX_HD_ENCODER_LIB_PATHS, "aptX-HD encoder");
  if (!aptx_hd_encoder_lib_handle) {
    return false;
  }

Loading