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

Commit 0b550610 authored by Patty Huang's avatar Patty Huang
Browse files

Add LE audio broadcast dynamic switch feature

If the device set ro.bluetooth.leaudio_broadcast_switcher.supported=true
and the hardware supports le audio required capabilities, the feature
could be switched via developer option

Bug: 236907310

Test: switch LE audio feature, and check LE audio functionality status
Change-Id: I2e5c4cdce2c2b52ae7bd696cf7752410d995d228
Merged-In: I2e5c4cdce2c2b52ae7bd696cf7752410d995d228
(cherry picked from commit 8a4d935e)
parent 7ab5716d
Loading
Loading
Loading
Loading
+10 −5
Original line number Diff line number Diff line
@@ -749,8 +749,9 @@ public class AdapterService extends Service {
            nonSupportedProfiles.add(BassClientService.class);
        }

        if (isLeAudioBroadcastSourceSupported()) {
            Config.addSupportedProfile(BluetoothProfile.LE_AUDIO_BROADCAST);
        if (!isLeAudioBroadcastSourceSupported()) {
            Config.updateSupportedProfileMask(
                    false, LeAudioService.class, BluetoothProfile.LE_AUDIO_BROADCAST);
        }

        if (!nonSupportedProfiles.isEmpty()) {
@@ -3399,7 +3400,8 @@ public class AdapterService extends Service {
                return BluetoothStatusCodes.ERROR_BLUETOOTH_NOT_ENABLED;
            }

            if (service.isLeAudioBroadcastSourceSupported()) {
            long supportBitMask = Config.getSupportedProfilesBitMask();
            if ((supportBitMask & (1 << BluetoothProfile.LE_AUDIO_BROADCAST)) != 0) {
                return BluetoothStatusCodes.FEATURE_SUPPORTED;
            }

@@ -4656,8 +4658,7 @@ public class AdapterService extends Service {
     * @return true, if the LE audio broadcast source is supported
     */
    public boolean isLeAudioBroadcastSourceSupported() {
        return  BluetoothProperties.isProfileBapBroadcastSourceEnabled().orElse(false)
                && mAdapterProperties.isLePeriodicAdvertisingSupported()
        return  mAdapterProperties.isLePeriodicAdvertisingSupported()
                && mAdapterProperties.isLeExtendedAdvertisingSupported()
                && mAdapterProperties.isLeIsochronousBroadcasterSupported();
    }
@@ -4674,6 +4675,10 @@ public class AdapterService extends Service {
                || mAdapterProperties.isLePeriodicAdvertisingSyncTransferRecipientSupported());
    }

    public long getSupportedProfilesBitMask() {
        return Config.getSupportedProfilesBitMask();
    }

    /**
     * Check if the LE audio CIS central feature is supported.
     *
+28 −4
Original line number Diff line number Diff line
@@ -60,10 +60,11 @@ public class Config {

    private static final String FEATURE_HEARING_AID = "settings_bluetooth_hearing_aid";
    private static final String FEATURE_BATTERY = "settings_bluetooth_battery";
    private static long sSupportedMask = 0;

    private static final String LE_AUDIO_DYNAMIC_SWITCH_PROPERTY =
            "ro.bluetooth.leaudio_switcher.supported";
    private static final String LE_AUDIO_BROADCAST_DYNAMIC_SWITCH_PROPERTY =
            "ro.bluetooth.leaudio_broadcast_switcher.supported";
    private static final String LE_AUDIO_DYNAMIC_ENABLED_PROPERTY =
            "persist.bluetooth.leaudio_switcher.enabled";

@@ -165,6 +166,11 @@ public class Config {
    private static boolean sIsGdEnabledUptoScanningLayer = false;

    static void init(Context ctx) {
        if (LeAudioService.isBroadcastEnabled()) {
            updateSupportedProfileMask(
                    true, LeAudioService.class, BluetoothProfile.LE_AUDIO_BROADCAST);
        }

        final boolean leAudioDynamicSwitchSupported =
                SystemProperties.getBoolean(LE_AUDIO_DYNAMIC_SWITCH_PROPERTY, false);

@@ -205,6 +211,15 @@ public class Config {
        setProfileEnabled(TbsService.class, enable);
        setProfileEnabled(McpService.class, enable);
        setProfileEnabled(VolumeControlService.class, enable);

        final boolean broadcastDynamicSwitchSupported =
                SystemProperties.getBoolean(LE_AUDIO_BROADCAST_DYNAMIC_SWITCH_PROPERTY, false);

        if (broadcastDynamicSwitchSupported) {
            setProfileEnabled(BassClientService.class, enable);
            updateSupportedProfileMask(
                    enable, LeAudioService.class, BluetoothProfile.LE_AUDIO_BROADCAST);
        }
    }

    /**
@@ -226,8 +241,17 @@ public class Config {
        sSupportedProfiles = profilesList.toArray(new Class[profilesList.size()]);
    }

    static void addSupportedProfile(int supportedProfile) {
        sSupportedMask |= (1 << supportedProfile);
    static void updateSupportedProfileMask(Boolean enable, Class profile, int supportedProfile) {
        for (ProfileConfig config : PROFILE_SERVICES_AND_FLAGS) {
            if (config.mClass == profile) {
                if (enable) {
                    config.mMask |= 1 << supportedProfile;
                } else {
                    config.mMask &= ~(1 << supportedProfile);
                }
                return;
            }
        }
    }

    static HashSet<Class> geLeAudioUnicastProfiles() {
@@ -253,7 +277,7 @@ public class Config {
    }

    static long getSupportedProfilesBitMask() {
        long mask = sSupportedMask;
        long mask = 0;
        for (final Class profileClass : getSupportedProfiles()) {
            mask |= getProfileMask(profileClass);
        }
+7 −1
Original line number Diff line number Diff line
@@ -194,6 +194,10 @@ public class LeAudioService extends ProfileService {
        return BluetoothProperties.isProfileBapUnicastClientEnabled().orElse(false);
    }

    public static boolean isBroadcastEnabled() {
        return BluetoothProperties.isProfileBapBroadcastSourceEnabled().orElse(false);
    }

    @Override
    protected void create() {
        Log.i(TAG, "create()");
@@ -252,7 +256,9 @@ public class LeAudioService extends ProfileService {
                LeAudioTmapGattServer.TMAP_ROLE_FLAG_CG | LeAudioTmapGattServer.TMAP_ROLE_FLAG_UMS;

        // Initialize Broadcast native interface
        if (mAdapterService.isLeAudioBroadcastSourceSupported()) {
        if ((mAdapterService.getSupportedProfilesBitMask()
                    & (1 << BluetoothProfile.LE_AUDIO_BROADCAST)) != 0) {
            Log.i(TAG, "Init Le Audio broadcaster");
            mBroadcastCallbacks = new RemoteCallbackList<IBluetoothLeBroadcastCallback>();
            mLeAudioBroadcasterNativeInterface = Objects.requireNonNull(
                    LeAudioBroadcasterNativeInterface.getInstance(),