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

Commit 9e932e5c authored by Treehugger Robot's avatar Treehugger Robot Committed by Automerger Merge Worker
Browse files

Merge changes Ib4399f9c,I744267ec am: 983005bb am: 5ac6010d

parents 84792238 5ac6010d
Loading
Loading
Loading
Loading
+5 −1
Original line number Original line Diff line number Diff line
@@ -439,6 +439,9 @@ public class LeAudioService extends ProfileService {
    }
    }


    BluetoothDevice getConnectedGroupLeadDevice(int groupId) {
    BluetoothDevice getConnectedGroupLeadDevice(int groupId) {
        if (mActiveAudioOutDevice != null) {
            return mActiveAudioOutDevice;
        }
        return getFirstDeviceFromGroup(groupId);
        return getFirstDeviceFromGroup(groupId);
    }
    }


@@ -2364,7 +2367,8 @@ public class LeAudioService extends ProfileService {
            ProfileService.println(sb, "    isActive: " + descriptor.mIsActive);
            ProfileService.println(sb, "    isActive: " + descriptor.mIsActive);
            ProfileService.println(sb, "    isConnected: " + descriptor.mIsConnected);
            ProfileService.println(sb, "    isConnected: " + descriptor.mIsConnected);
            ProfileService.println(sb, "    mActiveContexts: " + descriptor.mActiveContexts);
            ProfileService.println(sb, "    mActiveContexts: " + descriptor.mActiveContexts);
            ProfileService.println(sb, "    group lead: " + getFirstDeviceFromGroup(groupId));
            ProfileService.println(sb, "    group lead: " + getConnectedGroupLeadDevice(groupId));
            ProfileService.println(sb, "    first device: " + getFirstDeviceFromGroup(groupId));
        }
        }
    }
    }
}
}
+46 −15
Original line number Original line Diff line number Diff line
@@ -704,7 +704,11 @@ class LeAudioGroupStateMachineImpl : public LeAudioGroupStateMachine {
     * to streaming state.
     * to streaming state.
     */
     */
    struct ase* ase = leAudioDevice->GetFirstActiveAse();
    struct ase* ase = leAudioDevice->GetFirstActiveAse();
    LOG_ASSERT(ase) << __func__ << " shouldn't be called without an active ASE";
    ASSERT_LOG(ase != nullptr,
               "shouldn't be called without an active ASE, device %s, group "
               "id: %d, cis handle 0x%04x",
               leAudioDevice->address_.ToString().c_str(), event->cig_id,
               event->cis_conn_hdl);
    do {
    do {
      if (ase->direction == le_audio::types::kLeAudioDirectionSource)
      if (ase->direction == le_audio::types::kLeAudioDirectionSource)
        ids.push_back(ase->id);
        ids.push_back(ase->id);
@@ -793,15 +797,21 @@ class LeAudioGroupStateMachineImpl : public LeAudioGroupStateMachine {
         * is, otherwise stop the stream.
         * is, otherwise stop the stream.
         */
         */
        if (!group->HaveAllActiveDevicesCisDisc()) {
        if (!group->HaveAllActiveDevicesCisDisc()) {
          /* TODO: Reconfigure LC3 codec from here or maybe other place?*/
          /* There is ASE streaming for some device. Continue streaming. */
          LOG_WARN(
              "Group member disconnected during streaming. Cis handle 0x%04x",
              event->cis_conn_hdl);
          return;
          return;
        }
        }


        /*If there is no more ase to stream. Suspend audio and clear state
        LOG_INFO("Lost all members from the group %d", group->group_id_);
         * machine -> go to Idle */
        RemoveCigForGroup(group);

        group->SetState(AseState::BTA_LE_AUDIO_ASE_STATE_IDLE);
        group->SetTargetState(AseState::BTA_LE_AUDIO_ASE_STATE_IDLE);
        /* If there is no more ase to stream. Notify it is in IDLE. */
        state_machine_callbacks_->StatusReportCb(group->group_id_,
        state_machine_callbacks_->StatusReportCb(group->group_id_,
                                                 GroupStreamStatus::SUSPENDED);
                                                 GroupStreamStatus::IDLE);
        StopStream(group);
        return;
        return;


      case AseState::BTA_LE_AUDIO_ASE_STATE_QOS_CONFIGURED:
      case AseState::BTA_LE_AUDIO_ASE_STATE_QOS_CONFIGURED:
@@ -1120,6 +1130,17 @@ class LeAudioGroupStateMachineImpl : public LeAudioGroupStateMachine {
                AseState::BTA_LE_AUDIO_ASE_STATE_IDLE)) {
                AseState::BTA_LE_AUDIO_ASE_STATE_IDLE)) {
          /* More ASEs notification from this device has to come for this group
          /* More ASEs notification from this device has to come for this group
           */
           */
          LOG_DEBUG("Wait for more ASE to configure for device %s",
                    leAudioDevice->address_.ToString().c_str());
          return;
        }

        /* Before continue with release, make sure this is what is requested.
         * If not (e.g. only single device got disconnected), stop here
         */
        if (group->GetTargetState() != AseState::BTA_LE_AUDIO_ASE_STATE_IDLE) {
          LOG_DEBUG("Autonomus change of stated for device %s, ase id: %d",
                    leAudioDevice->address_.ToString().c_str(), ase->id);
          return;
          return;
        }
        }


@@ -1243,9 +1264,10 @@ class LeAudioGroupStateMachineImpl : public LeAudioGroupStateMachine {
            !ase->retrans_nb) {
            !ase->retrans_nb) {
          ase->max_transport_latency = rsp.max_transport_latency;
          ase->max_transport_latency = rsp.max_transport_latency;
          ase->retrans_nb = rsp.preferred_retrans_nb;
          ase->retrans_nb = rsp.preferred_retrans_nb;
          LOG(INFO) << __func__ << " Using server preferred QoS settings."
          LOG_INFO(
                    << " Max Transport Latency: " << +ase->max_transport_latency
              " Using server preferred QoS settings. Max Transport Latency: %d"
                    << ", Retransmission Number: " << +ase->retrans_nb;
              ", Retransmission Number: %d",
              +ase->max_transport_latency, ase->retrans_nb);
        }
        }
        ase->pres_delay_min = rsp.pres_delay_min;
        ase->pres_delay_min = rsp.pres_delay_min;
        ase->pres_delay_max = rsp.pres_delay_max;
        ase->pres_delay_max = rsp.pres_delay_max;
@@ -1256,13 +1278,16 @@ class LeAudioGroupStateMachineImpl : public LeAudioGroupStateMachine {


        if (group->GetTargetState() == AseState::BTA_LE_AUDIO_ASE_STATE_IDLE) {
        if (group->GetTargetState() == AseState::BTA_LE_AUDIO_ASE_STATE_IDLE) {
          /* This is autonomus change of the remote device */
          /* This is autonomus change of the remote device */
          LOG(INFO) << __func__ << " Autonomus change. Just store it. ";
          LOG_DEBUG("Autonomus change for device %s, ase id %d. Just store it.",
                    leAudioDevice->address_.ToString().c_str(), ase->id);
          return;
          return;
        }
        }


        if (leAudioDevice->HaveAnyUnconfiguredAses()) {
        if (leAudioDevice->HaveAnyUnconfiguredAses()) {
          /* More ASEs notification from this device has to come for this group
          /* More ASEs notification from this device has to come for this group
           */
           */
          LOG_DEBUG("More Ases to be configured for the device %s",
                    leAudioDevice->address_.ToString().c_str());
          return;
          return;
        }
        }


@@ -1404,6 +1429,17 @@ class LeAudioGroupStateMachineImpl : public LeAudioGroupStateMachine {
                AseState::BTA_LE_AUDIO_ASE_STATE_CODEC_CONFIGURED)) {
                AseState::BTA_LE_AUDIO_ASE_STATE_CODEC_CONFIGURED)) {
          /* More ASEs notification from this device has to come for this group
          /* More ASEs notification from this device has to come for this group
           */
           */
          LOG_DEBUG("Wait for more ASE to configure for device %s",
                    leAudioDevice->address_.ToString().c_str());
          return;
        }

        /* Before continue with release, make sure this is what is requested.
         * If not (e.g. only single device got disconnected), stop here
         */
        if (group->GetTargetState() != AseState::BTA_LE_AUDIO_ASE_STATE_IDLE) {
          LOG_DEBUG("Autonomus change of stated for device %s, ase id: %d",
                    leAudioDevice->address_.ToString().c_str(), ase->id);
          return;
          return;
        }
        }


@@ -1909,11 +1945,6 @@ class LeAudioGroupStateMachineImpl : public LeAudioGroupStateMachine {
      case AseState::BTA_LE_AUDIO_ASE_STATE_STREAMING: {
      case AseState::BTA_LE_AUDIO_ASE_STATE_STREAMING: {
        ase->state = AseState::BTA_LE_AUDIO_ASE_STATE_RELEASING;
        ase->state = AseState::BTA_LE_AUDIO_ASE_STATE_RELEASING;


        /* Since single ase gets into Releasing state, lets assume our new
         * target state is IDLE
         */
        SetTargetState(group, AseState::BTA_LE_AUDIO_ASE_STATE_IDLE);

        /* Happens when bi-directional completive ASE releasing state came */
        /* Happens when bi-directional completive ASE releasing state came */
        if (ase->data_path_state == AudioStreamDataPathState::CIS_DISCONNECTING)
        if (ase->data_path_state == AudioStreamDataPathState::CIS_DISCONNECTING)
          break;
          break;
+61 −1
Original line number Original line Diff line number Diff line
@@ -2146,7 +2146,11 @@ TEST_F(StateMachineTest, testAseAutonomousRelease) {
  // Validate new GroupStreamStatus
  // Validate new GroupStreamStatus
  EXPECT_CALL(mock_callbacks_,
  EXPECT_CALL(mock_callbacks_,
              StatusReportCb(leaudio_group_id,
              StatusReportCb(leaudio_group_id,
                             bluetooth::le_audio::GroupStreamStatus::IDLE));
                             bluetooth::le_audio::GroupStreamStatus::IDLE))
      .Times(AtLeast(1));

  /* Single disconnect as it is bidirectional Cis*/
  EXPECT_CALL(*mock_iso_manager_, DisconnectCis(_, _)).Times(1);


  for (auto* device = group->GetFirstDevice(); device != nullptr;
  for (auto* device = group->GetFirstDevice(); device != nullptr;
       device = group->GetNextDevice(device)) {
       device = group->GetNextDevice(device)) {
@@ -2173,6 +2177,62 @@ TEST_F(StateMachineTest, testAseAutonomousRelease) {
  }
  }
}
}


TEST_F(StateMachineTest, testAseAutonomousRelease2Devices) {
  const auto context_type = kContextTypeConversational;
  const int leaudio_group_id = 4;
  const int num_of_devices = 2;

  // Prepare fake connected device group
  auto* group = PrepareSingleTestDeviceGroup(leaudio_group_id, context_type,
                                             num_of_devices);

  /* Since we prepared device with Conversional context in mind, Sink and Source
   * ASEs should have been configured.
   */
  PrepareConfigureCodecHandler(group);
  PrepareConfigureQosHandler(group);
  PrepareEnableHandler(group);
  PrepareDisableHandler(group);
  PrepareReceiverStartReady(group);
  PrepareReceiverStopReady(group);
  PrepareReleaseHandler(group);

  InjectInitialIdleNotification(group);

  // Validate initial GroupStreamStatus
  EXPECT_CALL(
      mock_callbacks_,
      StatusReportCb(leaudio_group_id,
                     bluetooth::le_audio::GroupStreamStatus::STREAMING));

  // Start the configuration and stream Media content
  ASSERT_TRUE(LeAudioGroupStateMachine::Get()->StartStream(
      group, static_cast<types::LeAudioContextType>(context_type)));

  // Check streaming will continue
  EXPECT_CALL(mock_callbacks_,
              StatusReportCb(leaudio_group_id,
                             bluetooth::le_audio::GroupStreamStatus::IDLE))
      .Times(0);

  /* Single disconnect as it is bidirectional Cis*/
  EXPECT_CALL(*mock_iso_manager_, DisconnectCis(_, _)).Times(1);

  auto device = group->GetFirstDevice();
  for (auto& ase : device->ases_) {
    client_parser::ascs::ase_codec_configured_state_params
        codec_configured_state_params;

    ASSERT_EQ(ase.state, types::AseState::BTA_LE_AUDIO_ASE_STATE_STREAMING);

    // Simulate autonomus release for one device.
    InjectAseStateNotification(&ase, device, group, ascs::kAseStateReleasing,
                               &codec_configured_state_params);
    InjectAseStateNotification(&ase, device, group, ascs::kAseStateIdle,
                               &codec_configured_state_params);
  }
}

TEST_F(StateMachineTest, testStateTransitionTimeoutOnIdleState) {
TEST_F(StateMachineTest, testStateTransitionTimeoutOnIdleState) {
  const auto context_type = kContextTypeRingtone;
  const auto context_type = kContextTypeRingtone;
  const int leaudio_group_id = 4;
  const int leaudio_group_id = 4;