Loading audio/aidl/default/r_submix/StreamRemoteSubmix.cpp +17 −22 Original line number Diff line number Diff line Loading @@ -179,7 +179,7 @@ void StreamRemoteSubmix::shutdown() { LOG(ERROR) << __func__ << ": transfer without a pipe!"; return ::android::UNEXPECTED_NULL; } mCurrentRoute->exitStandby(mIsInput); return (mIsInput ? inRead(buffer, frameCount, actualFrameCount) : outWrite(buffer, frameCount, actualFrameCount)); } Loading @@ -190,17 +190,14 @@ void StreamRemoteSubmix::shutdown() { return ::android::NO_INIT; } const ssize_t framesInPipe = source->availableToRead(); if (framesInPipe < 0) { return ::android::INVALID_OPERATION; if (framesInPipe <= 0) { // No need to update the position frames return ::android::OK; } if (mIsInput) { position->frames += framesInPipe; } else { if (position->frames > framesInPipe) { } else if (position->frames >= framesInPipe) { position->frames -= framesInPipe; } else { position->frames = 0; } } return ::android::OK; } Loading Loading @@ -280,7 +277,6 @@ size_t StreamRemoteSubmix::getStreamPipeSizeInFrames() { size_t* actualFrameCount) { // about to read from audio source sp<MonoPipeReader> source = mCurrentRoute->getSource(); if (source == nullptr || source->availableToRead() == 0) { if (source == nullptr) { int readErrorCount = mCurrentRoute->notifyReadError(); if (readErrorCount < kMaxReadErrorLogs) { Loading @@ -290,9 +286,6 @@ size_t StreamRemoteSubmix::getStreamPipeSizeInFrames() { } else { LOG(ERROR) << __func__ << ": Read errors " << readErrorCount; } } else { LOG(INFO) << __func__ << ": no data to read yet, providing empty data"; } const size_t delayUs = static_cast<size_t>( std::roundf(frameCount * MICROS_PER_SECOND / mStreamConfig.sampleRate)); usleep(delayUs); Loading @@ -306,9 +299,10 @@ size_t StreamRemoteSubmix::getStreamPipeSizeInFrames() { const size_t delayUs = static_cast<size_t>(std::roundf(kReadAttemptSleepUs)); char* buff = (char*)buffer; size_t remainingFrames = frameCount; int availableToRead = source->availableToRead(); while ((remainingFrames > 0) && (attempts < kMaxReadFailureAttempts)) { LOG(VERBOSE) << __func__ << ": frames available to read " << source->availableToRead(); while ((remainingFrames > 0) && (availableToRead > 0) && (attempts < kMaxReadFailureAttempts)) { LOG(VERBOSE) << __func__ << ": frames available to read " << availableToRead; ssize_t framesRead = source->read(buff, remainingFrames); Loading @@ -317,6 +311,7 @@ size_t StreamRemoteSubmix::getStreamPipeSizeInFrames() { if (framesRead > 0) { remainingFrames -= framesRead; buff += framesRead * mStreamConfig.frameSize; availableToRead -= framesRead; LOG(VERBOSE) << __func__ << ": (attempts = " << attempts << ") got " << framesRead << " frames, remaining=" << remainingFrames; } else { Loading audio/aidl/vts/ModuleConfig.cpp +132 −38 Original line number Diff line number Diff line Loading @@ -66,15 +66,36 @@ std::optional<AudioOffloadInfo> ModuleConfig::generateOffloadInfoIfNeeded( return {}; } std::vector<aidl::android::media::audio::common::AudioPort> ModuleConfig::getAudioPortsForDeviceTypes(const std::vector<AudioDeviceType>& deviceTypes, const std::string& connection) { return getAudioPortsForDeviceTypes(mPorts, deviceTypes, connection); } // static std::vector<aidl::android::media::audio::common::AudioPort> ModuleConfig::getBuiltInMicPorts( const std::vector<aidl::android::media::audio::common::AudioPort>& ports) { return getAudioPortsForDeviceTypes( ports, std::vector<AudioDeviceType>{AudioDeviceType::IN_MICROPHONE, AudioDeviceType::IN_MICROPHONE_BACK}); } std::vector<aidl::android::media::audio::common::AudioPort> ModuleConfig::getAudioPortsForDeviceTypes( const std::vector<aidl::android::media::audio::common::AudioPort>& ports, const std::vector<AudioDeviceType>& deviceTypes, const std::string& connection) { std::vector<AudioPort> result; std::copy_if(ports.begin(), ports.end(), std::back_inserter(result), [](const auto& port) { const auto type = port.ext.template get<AudioPortExt::Tag::device>().device.type; return type.connection.empty() && (type.type == AudioDeviceType::IN_MICROPHONE || type.type == AudioDeviceType::IN_MICROPHONE_BACK); }); for (const auto& port : ports) { if (port.ext.getTag() != AudioPortExt::Tag::device) continue; const auto type = port.ext.get<AudioPortExt::Tag::device>().device.type; if (type.connection == connection) { for (auto deviceType : deviceTypes) { if (type.type == deviceType) { result.push_back(port); } } } } return result; } Loading Loading @@ -119,6 +140,31 @@ std::vector<AudioPort> ModuleConfig::getAttachedDevicePorts() const { return result; } std::vector<AudioPort> ModuleConfig::getConnectedExternalDevicePorts() const { std::vector<AudioPort> result; std::copy_if(mPorts.begin(), mPorts.end(), std::back_inserter(result), [&](const auto& port) { return mConnectedExternalSinkDevicePorts.count(port.id) != 0 || mConnectedExternalSourceDevicePorts.count(port.id) != 0; }); return result; } std::set<int32_t> ModuleConfig::getConnectedSinkDevicePorts() const { std::set<int32_t> result; result.insert(mAttachedSinkDevicePorts.begin(), mAttachedSinkDevicePorts.end()); result.insert(mConnectedExternalSinkDevicePorts.begin(), mConnectedExternalSinkDevicePorts.end()); return result; } std::set<int32_t> ModuleConfig::getConnectedSourceDevicePorts() const { std::set<int32_t> result; result.insert(mAttachedSourceDevicePorts.begin(), mAttachedSourceDevicePorts.end()); result.insert(mConnectedExternalSourceDevicePorts.begin(), mConnectedExternalSourceDevicePorts.end()); return result; } std::vector<AudioPort> ModuleConfig::getExternalDevicePorts() const { std::vector<AudioPort> result; std::copy_if(mPorts.begin(), mPorts.end(), std::back_inserter(result), Loading @@ -126,76 +172,77 @@ std::vector<AudioPort> ModuleConfig::getExternalDevicePorts() const { return result; } std::vector<AudioPort> ModuleConfig::getInputMixPorts(bool attachedOnly) const { std::vector<AudioPort> ModuleConfig::getInputMixPorts(bool connectedOnly) const { std::vector<AudioPort> result; std::copy_if(mPorts.begin(), mPorts.end(), std::back_inserter(result), [&](const auto& port) { return port.ext.getTag() == AudioPortExt::Tag::mix && port.flags.getTag() == AudioIoFlags::Tag::input && (!attachedOnly || !getAttachedSourceDevicesPortsForMixPort(port).empty()); (!connectedOnly || !getConnectedSourceDevicesPortsForMixPort(port).empty()); }); return result; } std::vector<AudioPort> ModuleConfig::getOutputMixPorts(bool attachedOnly) const { std::vector<AudioPort> ModuleConfig::getOutputMixPorts(bool connectedOnly) const { std::vector<AudioPort> result; std::copy_if(mPorts.begin(), mPorts.end(), std::back_inserter(result), [&](const auto& port) { return port.ext.getTag() == AudioPortExt::Tag::mix && port.flags.getTag() == AudioIoFlags::Tag::output && (!attachedOnly || !getAttachedSinkDevicesPortsForMixPort(port).empty()); (!connectedOnly || !getConnectedSinkDevicesPortsForMixPort(port).empty()); }); return result; } std::vector<AudioPort> ModuleConfig::getNonBlockingMixPorts(bool attachedOnly, std::vector<AudioPort> ModuleConfig::getNonBlockingMixPorts(bool connectedOnly, bool singlePort) const { return findMixPorts(false /*isInput*/, attachedOnly, singlePort, [&](const AudioPort& port) { return findMixPorts(false /*isInput*/, connectedOnly, singlePort, [&](const AudioPort& port) { return isBitPositionFlagSet(port.flags.get<AudioIoFlags::Tag::output>(), AudioOutputFlags::NON_BLOCKING); }); } std::vector<AudioPort> ModuleConfig::getOffloadMixPorts(bool attachedOnly, bool singlePort) const { return findMixPorts(false /*isInput*/, attachedOnly, singlePort, [&](const AudioPort& port) { std::vector<AudioPort> ModuleConfig::getOffloadMixPorts(bool connectedOnly, bool singlePort) const { return findMixPorts(false /*isInput*/, connectedOnly, singlePort, [&](const AudioPort& port) { return isBitPositionFlagSet(port.flags.get<AudioIoFlags::Tag::output>(), AudioOutputFlags::COMPRESS_OFFLOAD); }); } std::vector<AudioPort> ModuleConfig::getPrimaryMixPorts(bool attachedOnly, bool singlePort) const { return findMixPorts(false /*isInput*/, attachedOnly, singlePort, [&](const AudioPort& port) { std::vector<AudioPort> ModuleConfig::getPrimaryMixPorts(bool connectedOnly, bool singlePort) const { return findMixPorts(false /*isInput*/, connectedOnly, singlePort, [&](const AudioPort& port) { return isBitPositionFlagSet(port.flags.get<AudioIoFlags::Tag::output>(), AudioOutputFlags::PRIMARY); }); } std::vector<AudioPort> ModuleConfig::getMmapOutMixPorts(bool attachedOnly, bool singlePort) const { return findMixPorts(false /*isInput*/, attachedOnly, singlePort, [&](const AudioPort& port) { std::vector<AudioPort> ModuleConfig::getMmapOutMixPorts(bool connectedOnly, bool singlePort) const { return findMixPorts(false /*isInput*/, connectedOnly, singlePort, [&](const AudioPort& port) { return isBitPositionFlagSet(port.flags.get<AudioIoFlags::Tag::output>(), AudioOutputFlags::MMAP_NOIRQ); }); } std::vector<AudioPort> ModuleConfig::getMmapInMixPorts(bool attachedOnly, bool singlePort) const { return findMixPorts(true /*isInput*/, attachedOnly, singlePort, [&](const AudioPort& port) { std::vector<AudioPort> ModuleConfig::getMmapInMixPorts(bool connectedOnly, bool singlePort) const { return findMixPorts(true /*isInput*/, connectedOnly, singlePort, [&](const AudioPort& port) { return isBitPositionFlagSet(port.flags.get<AudioIoFlags::Tag::input>(), AudioInputFlags::MMAP_NOIRQ); }); } std::vector<AudioPort> ModuleConfig::getAttachedDevicesPortsForMixPort( std::vector<AudioPort> ModuleConfig::getConnectedDevicesPortsForMixPort( bool isInput, const AudioPortConfig& mixPortConfig) const { const auto mixPortIt = findById<AudioPort>(mPorts, mixPortConfig.portId); if (mixPortIt != mPorts.end()) { return getAttachedDevicesPortsForMixPort(isInput, *mixPortIt); return getConnectedDevicesPortsForMixPort(isInput, *mixPortIt); } return {}; } std::vector<AudioPort> ModuleConfig::getAttachedSinkDevicesPortsForMixPort( std::vector<AudioPort> ModuleConfig::getConnectedSinkDevicesPortsForMixPort( const AudioPort& mixPort) const { std::vector<AudioPort> result; std::set<int32_t> connectedSinkDevicePorts = getConnectedSinkDevicePorts(); for (const auto& route : mRoutes) { if (mAttachedSinkDevicePorts.count(route.sinkPortId) != 0 && if ((connectedSinkDevicePorts.count(route.sinkPortId) != 0) && std::find(route.sourcePortIds.begin(), route.sourcePortIds.end(), mixPort.id) != route.sourcePortIds.end()) { const auto devicePortIt = findById<AudioPort>(mPorts, route.sinkPortId); Loading @@ -205,13 +252,14 @@ std::vector<AudioPort> ModuleConfig::getAttachedSinkDevicesPortsForMixPort( return result; } std::vector<AudioPort> ModuleConfig::getAttachedSourceDevicesPortsForMixPort( std::vector<AudioPort> ModuleConfig::getConnectedSourceDevicesPortsForMixPort( const AudioPort& mixPort) const { std::vector<AudioPort> result; std::set<int32_t> connectedSourceDevicePorts = getConnectedSourceDevicePorts(); for (const auto& route : mRoutes) { if (route.sinkPortId == mixPort.id) { for (const auto srcId : route.sourcePortIds) { if (mAttachedSourceDevicePorts.count(srcId) != 0) { if (connectedSourceDevicePorts.count(srcId) != 0) { const auto devicePortIt = findById<AudioPort>(mPorts, srcId); if (devicePortIt != mPorts.end()) result.push_back(*devicePortIt); } Loading @@ -221,9 +269,10 @@ std::vector<AudioPort> ModuleConfig::getAttachedSourceDevicesPortsForMixPort( return result; } std::optional<AudioPort> ModuleConfig::getSourceMixPortForAttachedDevice() const { std::optional<AudioPort> ModuleConfig::getSourceMixPortForConnectedDevice() const { std::set<int32_t> connectedSinkDevicePorts = getConnectedSinkDevicePorts(); for (const auto& route : mRoutes) { if (mAttachedSinkDevicePorts.count(route.sinkPortId) != 0) { if (connectedSinkDevicePorts.count(route.sinkPortId) != 0) { const auto mixPortIt = findById<AudioPort>(mPorts, route.sourcePortIds[0]); if (mixPortIt != mPorts.end()) return *mixPortIt; } Loading @@ -233,7 +282,7 @@ std::optional<AudioPort> ModuleConfig::getSourceMixPortForAttachedDevice() const std::optional<ModuleConfig::SrcSinkPair> ModuleConfig::getNonRoutableSrcSinkPair( bool isInput) const { const auto mixPorts = getMixPorts(isInput, false /*attachedOnly*/); const auto mixPorts = getMixPorts(isInput, false /*connectedOnly*/); std::set<std::pair<int32_t, int32_t>> allowedRoutes; for (const auto& route : mRoutes) { for (const auto srcPortId : route.sourcePortIds) { Loading @@ -243,7 +292,8 @@ std::optional<ModuleConfig::SrcSinkPair> ModuleConfig::getNonRoutableSrcSinkPair auto make_pair = [isInput](auto& device, auto& mix) { return isInput ? std::make_pair(device, mix) : std::make_pair(mix, device); }; for (const auto portId : isInput ? mAttachedSourceDevicePorts : mAttachedSinkDevicePorts) { for (const auto portId : isInput ? getConnectedSourceDevicePorts() : getConnectedSinkDevicePorts()) { const auto devicePortIt = findById<AudioPort>(mPorts, portId); if (devicePortIt == mPorts.end()) continue; auto devicePortConfig = getSingleConfigForDevicePort(*devicePortIt); Loading @@ -262,10 +312,11 @@ std::optional<ModuleConfig::SrcSinkPair> ModuleConfig::getNonRoutableSrcSinkPair std::optional<ModuleConfig::SrcSinkPair> ModuleConfig::getRoutableSrcSinkPair(bool isInput) const { if (isInput) { std::set<int32_t> connectedSourceDevicePorts = getConnectedSourceDevicePorts(); for (const auto& route : mRoutes) { auto srcPortIdIt = std::find_if( route.sourcePortIds.begin(), route.sourcePortIds.end(), [&](const auto& portId) { return mAttachedSourceDevicePorts.count(portId); }); [&](const auto& portId) { return connectedSourceDevicePorts.count(portId); }); if (srcPortIdIt == route.sourcePortIds.end()) continue; const auto devicePortIt = findById<AudioPort>(mPorts, *srcPortIdIt); const auto mixPortIt = findById<AudioPort>(mPorts, route.sinkPortId); Loading @@ -276,8 +327,9 @@ std::optional<ModuleConfig::SrcSinkPair> ModuleConfig::getRoutableSrcSinkPair(bo return std::make_pair(devicePortConfig, mixPortConfig.value()); } } else { std::set<int32_t> connectedSinkDevicePorts = getConnectedSinkDevicePorts(); for (const auto& route : mRoutes) { if (mAttachedSinkDevicePorts.count(route.sinkPortId) == 0) continue; if (connectedSinkDevicePorts.count(route.sinkPortId) == 0) continue; const auto mixPortIt = findById<AudioPort>(mPorts, route.sourcePortIds[0]); const auto devicePortIt = findById<AudioPort>(mPorts, route.sinkPortId); if (devicePortIt == mPorts.end() || mixPortIt == mPorts.end()) continue; Loading @@ -293,11 +345,12 @@ std::optional<ModuleConfig::SrcSinkPair> ModuleConfig::getRoutableSrcSinkPair(bo std::vector<ModuleConfig::SrcSinkGroup> ModuleConfig::getRoutableSrcSinkGroups(bool isInput) const { std::vector<SrcSinkGroup> result; if (isInput) { std::set<int32_t> connectedSourceDevicePorts = getConnectedSourceDevicePorts(); for (const auto& route : mRoutes) { std::vector<int32_t> srcPortIds; std::copy_if(route.sourcePortIds.begin(), route.sourcePortIds.end(), std::back_inserter(srcPortIds), [&](const auto& portId) { return mAttachedSourceDevicePorts.count(portId); return connectedSourceDevicePorts.count(portId); }); if (srcPortIds.empty()) continue; const auto mixPortIt = findById<AudioPort>(mPorts, route.sinkPortId); Loading @@ -317,8 +370,9 @@ std::vector<ModuleConfig::SrcSinkGroup> ModuleConfig::getRoutableSrcSinkGroups(b } } } else { std::set<int32_t> connectedSinkDevicePorts = getConnectedSinkDevicePorts(); for (const auto& route : mRoutes) { if (mAttachedSinkDevicePorts.count(route.sinkPortId) == 0) continue; if (connectedSinkDevicePorts.count(route.sinkPortId) == 0) continue; const auto devicePortIt = findById<AudioPort>(mPorts, route.sinkPortId); if (devicePortIt == mPorts.end()) continue; auto devicePortConfig = getSingleConfigForDevicePort(*devicePortIt); Loading Loading @@ -352,6 +406,8 @@ std::string ModuleConfig::toString() const { result.append(android::internal::ToString(mAttachedSourceDevicePorts)); result.append("\nExternal device ports: "); result.append(android::internal::ToString(mExternalDevicePorts)); result.append("\nConnected external device ports: "); result.append(android::internal::ToString(getConnectedExternalDevicePorts())); result.append("\nRoutes: "); result.append(android::internal::ToString(mRoutes)); return result; Loading Loading @@ -384,10 +440,10 @@ static bool isDynamicProfile(const AudioProfile& profile) { } std::vector<AudioPort> ModuleConfig::findMixPorts( bool isInput, bool attachedOnly, bool singlePort, bool isInput, bool connectedOnly, bool singlePort, const std::function<bool(const AudioPort&)>& pred) const { std::vector<AudioPort> result; const auto mixPorts = getMixPorts(isInput, attachedOnly); const auto mixPorts = getMixPorts(isInput, connectedOnly); for (auto mixPortIt = mixPorts.begin(); mixPortIt != mixPorts.end();) { mixPortIt = std::find_if(mixPortIt, mixPorts.end(), pred); if (mixPortIt == mixPorts.end()) break; Loading @@ -401,7 +457,7 @@ std::vector<AudioPortConfig> ModuleConfig::generateAudioMixPortConfigs( const std::vector<AudioPort>& ports, bool isInput, bool singleProfile) const { std::vector<AudioPortConfig> result; for (const auto& mixPort : ports) { if (getAttachedDevicesPortsForMixPort(isInput, mixPort).empty()) { if (getConnectedDevicesPortsForMixPort(isInput, mixPort).empty()) { continue; } for (const auto& profile : mixPort.profiles) { Loading Loading @@ -443,10 +499,48 @@ std::vector<AudioPortConfig> ModuleConfig::generateAudioDevicePortConfigs( return result; } const ndk::ScopedAStatus& ModuleConfig::onExternalDeviceConnected(IModule* module, const AudioPort& port) { // Update ports and routes mStatus = module->getAudioPorts(&mPorts); if (!mStatus.isOk()) return mStatus; mStatus = module->getAudioRoutes(&mRoutes); if (!mStatus.isOk()) return mStatus; // Validate port is present in module if (std::find(mPorts.begin(), mPorts.end(), port) == mPorts.end()) { mStatus = ndk::ScopedAStatus::fromExceptionCode(EX_ILLEGAL_STATE); return mStatus; } if (port.flags.getTag() == aidl::android::media::audio::common::AudioIoFlags::Tag::input) { mConnectedExternalSourceDevicePorts.insert(port.id); } else { mConnectedExternalSinkDevicePorts.insert(port.id); } return mStatus; } const ndk::ScopedAStatus& ModuleConfig::onExternalDeviceDisconnected(IModule* module, const AudioPort& port) { // Update ports and routes mStatus = module->getAudioPorts(&mPorts); if (!mStatus.isOk()) return mStatus; mStatus = module->getAudioRoutes(&mRoutes); if (!mStatus.isOk()) return mStatus; if (port.flags.getTag() == aidl::android::media::audio::common::AudioIoFlags::Tag::input) { mConnectedExternalSourceDevicePorts.erase(port.id); } else { mConnectedExternalSinkDevicePorts.erase(port.id); } return mStatus; } bool ModuleConfig::isMmapSupported() const { const std::vector<AudioPort> mmapOutMixPorts = getMmapOutMixPorts(false /*attachedOnly*/, false /*singlePort*/); getMmapOutMixPorts(false /*connectedOnly*/, false /*singlePort*/); const std::vector<AudioPort> mmapInMixPorts = getMmapInMixPorts(false /*attachedOnly*/, false /*singlePort*/); getMmapInMixPorts(false /*connectedOnly*/, false /*singlePort*/); return !mmapOutMixPorts.empty() || !mmapInMixPorts.empty(); } Loading
audio/aidl/default/r_submix/StreamRemoteSubmix.cpp +17 −22 Original line number Diff line number Diff line Loading @@ -179,7 +179,7 @@ void StreamRemoteSubmix::shutdown() { LOG(ERROR) << __func__ << ": transfer without a pipe!"; return ::android::UNEXPECTED_NULL; } mCurrentRoute->exitStandby(mIsInput); return (mIsInput ? inRead(buffer, frameCount, actualFrameCount) : outWrite(buffer, frameCount, actualFrameCount)); } Loading @@ -190,17 +190,14 @@ void StreamRemoteSubmix::shutdown() { return ::android::NO_INIT; } const ssize_t framesInPipe = source->availableToRead(); if (framesInPipe < 0) { return ::android::INVALID_OPERATION; if (framesInPipe <= 0) { // No need to update the position frames return ::android::OK; } if (mIsInput) { position->frames += framesInPipe; } else { if (position->frames > framesInPipe) { } else if (position->frames >= framesInPipe) { position->frames -= framesInPipe; } else { position->frames = 0; } } return ::android::OK; } Loading Loading @@ -280,7 +277,6 @@ size_t StreamRemoteSubmix::getStreamPipeSizeInFrames() { size_t* actualFrameCount) { // about to read from audio source sp<MonoPipeReader> source = mCurrentRoute->getSource(); if (source == nullptr || source->availableToRead() == 0) { if (source == nullptr) { int readErrorCount = mCurrentRoute->notifyReadError(); if (readErrorCount < kMaxReadErrorLogs) { Loading @@ -290,9 +286,6 @@ size_t StreamRemoteSubmix::getStreamPipeSizeInFrames() { } else { LOG(ERROR) << __func__ << ": Read errors " << readErrorCount; } } else { LOG(INFO) << __func__ << ": no data to read yet, providing empty data"; } const size_t delayUs = static_cast<size_t>( std::roundf(frameCount * MICROS_PER_SECOND / mStreamConfig.sampleRate)); usleep(delayUs); Loading @@ -306,9 +299,10 @@ size_t StreamRemoteSubmix::getStreamPipeSizeInFrames() { const size_t delayUs = static_cast<size_t>(std::roundf(kReadAttemptSleepUs)); char* buff = (char*)buffer; size_t remainingFrames = frameCount; int availableToRead = source->availableToRead(); while ((remainingFrames > 0) && (attempts < kMaxReadFailureAttempts)) { LOG(VERBOSE) << __func__ << ": frames available to read " << source->availableToRead(); while ((remainingFrames > 0) && (availableToRead > 0) && (attempts < kMaxReadFailureAttempts)) { LOG(VERBOSE) << __func__ << ": frames available to read " << availableToRead; ssize_t framesRead = source->read(buff, remainingFrames); Loading @@ -317,6 +311,7 @@ size_t StreamRemoteSubmix::getStreamPipeSizeInFrames() { if (framesRead > 0) { remainingFrames -= framesRead; buff += framesRead * mStreamConfig.frameSize; availableToRead -= framesRead; LOG(VERBOSE) << __func__ << ": (attempts = " << attempts << ") got " << framesRead << " frames, remaining=" << remainingFrames; } else { Loading
audio/aidl/vts/ModuleConfig.cpp +132 −38 Original line number Diff line number Diff line Loading @@ -66,15 +66,36 @@ std::optional<AudioOffloadInfo> ModuleConfig::generateOffloadInfoIfNeeded( return {}; } std::vector<aidl::android::media::audio::common::AudioPort> ModuleConfig::getAudioPortsForDeviceTypes(const std::vector<AudioDeviceType>& deviceTypes, const std::string& connection) { return getAudioPortsForDeviceTypes(mPorts, deviceTypes, connection); } // static std::vector<aidl::android::media::audio::common::AudioPort> ModuleConfig::getBuiltInMicPorts( const std::vector<aidl::android::media::audio::common::AudioPort>& ports) { return getAudioPortsForDeviceTypes( ports, std::vector<AudioDeviceType>{AudioDeviceType::IN_MICROPHONE, AudioDeviceType::IN_MICROPHONE_BACK}); } std::vector<aidl::android::media::audio::common::AudioPort> ModuleConfig::getAudioPortsForDeviceTypes( const std::vector<aidl::android::media::audio::common::AudioPort>& ports, const std::vector<AudioDeviceType>& deviceTypes, const std::string& connection) { std::vector<AudioPort> result; std::copy_if(ports.begin(), ports.end(), std::back_inserter(result), [](const auto& port) { const auto type = port.ext.template get<AudioPortExt::Tag::device>().device.type; return type.connection.empty() && (type.type == AudioDeviceType::IN_MICROPHONE || type.type == AudioDeviceType::IN_MICROPHONE_BACK); }); for (const auto& port : ports) { if (port.ext.getTag() != AudioPortExt::Tag::device) continue; const auto type = port.ext.get<AudioPortExt::Tag::device>().device.type; if (type.connection == connection) { for (auto deviceType : deviceTypes) { if (type.type == deviceType) { result.push_back(port); } } } } return result; } Loading Loading @@ -119,6 +140,31 @@ std::vector<AudioPort> ModuleConfig::getAttachedDevicePorts() const { return result; } std::vector<AudioPort> ModuleConfig::getConnectedExternalDevicePorts() const { std::vector<AudioPort> result; std::copy_if(mPorts.begin(), mPorts.end(), std::back_inserter(result), [&](const auto& port) { return mConnectedExternalSinkDevicePorts.count(port.id) != 0 || mConnectedExternalSourceDevicePorts.count(port.id) != 0; }); return result; } std::set<int32_t> ModuleConfig::getConnectedSinkDevicePorts() const { std::set<int32_t> result; result.insert(mAttachedSinkDevicePorts.begin(), mAttachedSinkDevicePorts.end()); result.insert(mConnectedExternalSinkDevicePorts.begin(), mConnectedExternalSinkDevicePorts.end()); return result; } std::set<int32_t> ModuleConfig::getConnectedSourceDevicePorts() const { std::set<int32_t> result; result.insert(mAttachedSourceDevicePorts.begin(), mAttachedSourceDevicePorts.end()); result.insert(mConnectedExternalSourceDevicePorts.begin(), mConnectedExternalSourceDevicePorts.end()); return result; } std::vector<AudioPort> ModuleConfig::getExternalDevicePorts() const { std::vector<AudioPort> result; std::copy_if(mPorts.begin(), mPorts.end(), std::back_inserter(result), Loading @@ -126,76 +172,77 @@ std::vector<AudioPort> ModuleConfig::getExternalDevicePorts() const { return result; } std::vector<AudioPort> ModuleConfig::getInputMixPorts(bool attachedOnly) const { std::vector<AudioPort> ModuleConfig::getInputMixPorts(bool connectedOnly) const { std::vector<AudioPort> result; std::copy_if(mPorts.begin(), mPorts.end(), std::back_inserter(result), [&](const auto& port) { return port.ext.getTag() == AudioPortExt::Tag::mix && port.flags.getTag() == AudioIoFlags::Tag::input && (!attachedOnly || !getAttachedSourceDevicesPortsForMixPort(port).empty()); (!connectedOnly || !getConnectedSourceDevicesPortsForMixPort(port).empty()); }); return result; } std::vector<AudioPort> ModuleConfig::getOutputMixPorts(bool attachedOnly) const { std::vector<AudioPort> ModuleConfig::getOutputMixPorts(bool connectedOnly) const { std::vector<AudioPort> result; std::copy_if(mPorts.begin(), mPorts.end(), std::back_inserter(result), [&](const auto& port) { return port.ext.getTag() == AudioPortExt::Tag::mix && port.flags.getTag() == AudioIoFlags::Tag::output && (!attachedOnly || !getAttachedSinkDevicesPortsForMixPort(port).empty()); (!connectedOnly || !getConnectedSinkDevicesPortsForMixPort(port).empty()); }); return result; } std::vector<AudioPort> ModuleConfig::getNonBlockingMixPorts(bool attachedOnly, std::vector<AudioPort> ModuleConfig::getNonBlockingMixPorts(bool connectedOnly, bool singlePort) const { return findMixPorts(false /*isInput*/, attachedOnly, singlePort, [&](const AudioPort& port) { return findMixPorts(false /*isInput*/, connectedOnly, singlePort, [&](const AudioPort& port) { return isBitPositionFlagSet(port.flags.get<AudioIoFlags::Tag::output>(), AudioOutputFlags::NON_BLOCKING); }); } std::vector<AudioPort> ModuleConfig::getOffloadMixPorts(bool attachedOnly, bool singlePort) const { return findMixPorts(false /*isInput*/, attachedOnly, singlePort, [&](const AudioPort& port) { std::vector<AudioPort> ModuleConfig::getOffloadMixPorts(bool connectedOnly, bool singlePort) const { return findMixPorts(false /*isInput*/, connectedOnly, singlePort, [&](const AudioPort& port) { return isBitPositionFlagSet(port.flags.get<AudioIoFlags::Tag::output>(), AudioOutputFlags::COMPRESS_OFFLOAD); }); } std::vector<AudioPort> ModuleConfig::getPrimaryMixPorts(bool attachedOnly, bool singlePort) const { return findMixPorts(false /*isInput*/, attachedOnly, singlePort, [&](const AudioPort& port) { std::vector<AudioPort> ModuleConfig::getPrimaryMixPorts(bool connectedOnly, bool singlePort) const { return findMixPorts(false /*isInput*/, connectedOnly, singlePort, [&](const AudioPort& port) { return isBitPositionFlagSet(port.flags.get<AudioIoFlags::Tag::output>(), AudioOutputFlags::PRIMARY); }); } std::vector<AudioPort> ModuleConfig::getMmapOutMixPorts(bool attachedOnly, bool singlePort) const { return findMixPorts(false /*isInput*/, attachedOnly, singlePort, [&](const AudioPort& port) { std::vector<AudioPort> ModuleConfig::getMmapOutMixPorts(bool connectedOnly, bool singlePort) const { return findMixPorts(false /*isInput*/, connectedOnly, singlePort, [&](const AudioPort& port) { return isBitPositionFlagSet(port.flags.get<AudioIoFlags::Tag::output>(), AudioOutputFlags::MMAP_NOIRQ); }); } std::vector<AudioPort> ModuleConfig::getMmapInMixPorts(bool attachedOnly, bool singlePort) const { return findMixPorts(true /*isInput*/, attachedOnly, singlePort, [&](const AudioPort& port) { std::vector<AudioPort> ModuleConfig::getMmapInMixPorts(bool connectedOnly, bool singlePort) const { return findMixPorts(true /*isInput*/, connectedOnly, singlePort, [&](const AudioPort& port) { return isBitPositionFlagSet(port.flags.get<AudioIoFlags::Tag::input>(), AudioInputFlags::MMAP_NOIRQ); }); } std::vector<AudioPort> ModuleConfig::getAttachedDevicesPortsForMixPort( std::vector<AudioPort> ModuleConfig::getConnectedDevicesPortsForMixPort( bool isInput, const AudioPortConfig& mixPortConfig) const { const auto mixPortIt = findById<AudioPort>(mPorts, mixPortConfig.portId); if (mixPortIt != mPorts.end()) { return getAttachedDevicesPortsForMixPort(isInput, *mixPortIt); return getConnectedDevicesPortsForMixPort(isInput, *mixPortIt); } return {}; } std::vector<AudioPort> ModuleConfig::getAttachedSinkDevicesPortsForMixPort( std::vector<AudioPort> ModuleConfig::getConnectedSinkDevicesPortsForMixPort( const AudioPort& mixPort) const { std::vector<AudioPort> result; std::set<int32_t> connectedSinkDevicePorts = getConnectedSinkDevicePorts(); for (const auto& route : mRoutes) { if (mAttachedSinkDevicePorts.count(route.sinkPortId) != 0 && if ((connectedSinkDevicePorts.count(route.sinkPortId) != 0) && std::find(route.sourcePortIds.begin(), route.sourcePortIds.end(), mixPort.id) != route.sourcePortIds.end()) { const auto devicePortIt = findById<AudioPort>(mPorts, route.sinkPortId); Loading @@ -205,13 +252,14 @@ std::vector<AudioPort> ModuleConfig::getAttachedSinkDevicesPortsForMixPort( return result; } std::vector<AudioPort> ModuleConfig::getAttachedSourceDevicesPortsForMixPort( std::vector<AudioPort> ModuleConfig::getConnectedSourceDevicesPortsForMixPort( const AudioPort& mixPort) const { std::vector<AudioPort> result; std::set<int32_t> connectedSourceDevicePorts = getConnectedSourceDevicePorts(); for (const auto& route : mRoutes) { if (route.sinkPortId == mixPort.id) { for (const auto srcId : route.sourcePortIds) { if (mAttachedSourceDevicePorts.count(srcId) != 0) { if (connectedSourceDevicePorts.count(srcId) != 0) { const auto devicePortIt = findById<AudioPort>(mPorts, srcId); if (devicePortIt != mPorts.end()) result.push_back(*devicePortIt); } Loading @@ -221,9 +269,10 @@ std::vector<AudioPort> ModuleConfig::getAttachedSourceDevicesPortsForMixPort( return result; } std::optional<AudioPort> ModuleConfig::getSourceMixPortForAttachedDevice() const { std::optional<AudioPort> ModuleConfig::getSourceMixPortForConnectedDevice() const { std::set<int32_t> connectedSinkDevicePorts = getConnectedSinkDevicePorts(); for (const auto& route : mRoutes) { if (mAttachedSinkDevicePorts.count(route.sinkPortId) != 0) { if (connectedSinkDevicePorts.count(route.sinkPortId) != 0) { const auto mixPortIt = findById<AudioPort>(mPorts, route.sourcePortIds[0]); if (mixPortIt != mPorts.end()) return *mixPortIt; } Loading @@ -233,7 +282,7 @@ std::optional<AudioPort> ModuleConfig::getSourceMixPortForAttachedDevice() const std::optional<ModuleConfig::SrcSinkPair> ModuleConfig::getNonRoutableSrcSinkPair( bool isInput) const { const auto mixPorts = getMixPorts(isInput, false /*attachedOnly*/); const auto mixPorts = getMixPorts(isInput, false /*connectedOnly*/); std::set<std::pair<int32_t, int32_t>> allowedRoutes; for (const auto& route : mRoutes) { for (const auto srcPortId : route.sourcePortIds) { Loading @@ -243,7 +292,8 @@ std::optional<ModuleConfig::SrcSinkPair> ModuleConfig::getNonRoutableSrcSinkPair auto make_pair = [isInput](auto& device, auto& mix) { return isInput ? std::make_pair(device, mix) : std::make_pair(mix, device); }; for (const auto portId : isInput ? mAttachedSourceDevicePorts : mAttachedSinkDevicePorts) { for (const auto portId : isInput ? getConnectedSourceDevicePorts() : getConnectedSinkDevicePorts()) { const auto devicePortIt = findById<AudioPort>(mPorts, portId); if (devicePortIt == mPorts.end()) continue; auto devicePortConfig = getSingleConfigForDevicePort(*devicePortIt); Loading @@ -262,10 +312,11 @@ std::optional<ModuleConfig::SrcSinkPair> ModuleConfig::getNonRoutableSrcSinkPair std::optional<ModuleConfig::SrcSinkPair> ModuleConfig::getRoutableSrcSinkPair(bool isInput) const { if (isInput) { std::set<int32_t> connectedSourceDevicePorts = getConnectedSourceDevicePorts(); for (const auto& route : mRoutes) { auto srcPortIdIt = std::find_if( route.sourcePortIds.begin(), route.sourcePortIds.end(), [&](const auto& portId) { return mAttachedSourceDevicePorts.count(portId); }); [&](const auto& portId) { return connectedSourceDevicePorts.count(portId); }); if (srcPortIdIt == route.sourcePortIds.end()) continue; const auto devicePortIt = findById<AudioPort>(mPorts, *srcPortIdIt); const auto mixPortIt = findById<AudioPort>(mPorts, route.sinkPortId); Loading @@ -276,8 +327,9 @@ std::optional<ModuleConfig::SrcSinkPair> ModuleConfig::getRoutableSrcSinkPair(bo return std::make_pair(devicePortConfig, mixPortConfig.value()); } } else { std::set<int32_t> connectedSinkDevicePorts = getConnectedSinkDevicePorts(); for (const auto& route : mRoutes) { if (mAttachedSinkDevicePorts.count(route.sinkPortId) == 0) continue; if (connectedSinkDevicePorts.count(route.sinkPortId) == 0) continue; const auto mixPortIt = findById<AudioPort>(mPorts, route.sourcePortIds[0]); const auto devicePortIt = findById<AudioPort>(mPorts, route.sinkPortId); if (devicePortIt == mPorts.end() || mixPortIt == mPorts.end()) continue; Loading @@ -293,11 +345,12 @@ std::optional<ModuleConfig::SrcSinkPair> ModuleConfig::getRoutableSrcSinkPair(bo std::vector<ModuleConfig::SrcSinkGroup> ModuleConfig::getRoutableSrcSinkGroups(bool isInput) const { std::vector<SrcSinkGroup> result; if (isInput) { std::set<int32_t> connectedSourceDevicePorts = getConnectedSourceDevicePorts(); for (const auto& route : mRoutes) { std::vector<int32_t> srcPortIds; std::copy_if(route.sourcePortIds.begin(), route.sourcePortIds.end(), std::back_inserter(srcPortIds), [&](const auto& portId) { return mAttachedSourceDevicePorts.count(portId); return connectedSourceDevicePorts.count(portId); }); if (srcPortIds.empty()) continue; const auto mixPortIt = findById<AudioPort>(mPorts, route.sinkPortId); Loading @@ -317,8 +370,9 @@ std::vector<ModuleConfig::SrcSinkGroup> ModuleConfig::getRoutableSrcSinkGroups(b } } } else { std::set<int32_t> connectedSinkDevicePorts = getConnectedSinkDevicePorts(); for (const auto& route : mRoutes) { if (mAttachedSinkDevicePorts.count(route.sinkPortId) == 0) continue; if (connectedSinkDevicePorts.count(route.sinkPortId) == 0) continue; const auto devicePortIt = findById<AudioPort>(mPorts, route.sinkPortId); if (devicePortIt == mPorts.end()) continue; auto devicePortConfig = getSingleConfigForDevicePort(*devicePortIt); Loading Loading @@ -352,6 +406,8 @@ std::string ModuleConfig::toString() const { result.append(android::internal::ToString(mAttachedSourceDevicePorts)); result.append("\nExternal device ports: "); result.append(android::internal::ToString(mExternalDevicePorts)); result.append("\nConnected external device ports: "); result.append(android::internal::ToString(getConnectedExternalDevicePorts())); result.append("\nRoutes: "); result.append(android::internal::ToString(mRoutes)); return result; Loading Loading @@ -384,10 +440,10 @@ static bool isDynamicProfile(const AudioProfile& profile) { } std::vector<AudioPort> ModuleConfig::findMixPorts( bool isInput, bool attachedOnly, bool singlePort, bool isInput, bool connectedOnly, bool singlePort, const std::function<bool(const AudioPort&)>& pred) const { std::vector<AudioPort> result; const auto mixPorts = getMixPorts(isInput, attachedOnly); const auto mixPorts = getMixPorts(isInput, connectedOnly); for (auto mixPortIt = mixPorts.begin(); mixPortIt != mixPorts.end();) { mixPortIt = std::find_if(mixPortIt, mixPorts.end(), pred); if (mixPortIt == mixPorts.end()) break; Loading @@ -401,7 +457,7 @@ std::vector<AudioPortConfig> ModuleConfig::generateAudioMixPortConfigs( const std::vector<AudioPort>& ports, bool isInput, bool singleProfile) const { std::vector<AudioPortConfig> result; for (const auto& mixPort : ports) { if (getAttachedDevicesPortsForMixPort(isInput, mixPort).empty()) { if (getConnectedDevicesPortsForMixPort(isInput, mixPort).empty()) { continue; } for (const auto& profile : mixPort.profiles) { Loading Loading @@ -443,10 +499,48 @@ std::vector<AudioPortConfig> ModuleConfig::generateAudioDevicePortConfigs( return result; } const ndk::ScopedAStatus& ModuleConfig::onExternalDeviceConnected(IModule* module, const AudioPort& port) { // Update ports and routes mStatus = module->getAudioPorts(&mPorts); if (!mStatus.isOk()) return mStatus; mStatus = module->getAudioRoutes(&mRoutes); if (!mStatus.isOk()) return mStatus; // Validate port is present in module if (std::find(mPorts.begin(), mPorts.end(), port) == mPorts.end()) { mStatus = ndk::ScopedAStatus::fromExceptionCode(EX_ILLEGAL_STATE); return mStatus; } if (port.flags.getTag() == aidl::android::media::audio::common::AudioIoFlags::Tag::input) { mConnectedExternalSourceDevicePorts.insert(port.id); } else { mConnectedExternalSinkDevicePorts.insert(port.id); } return mStatus; } const ndk::ScopedAStatus& ModuleConfig::onExternalDeviceDisconnected(IModule* module, const AudioPort& port) { // Update ports and routes mStatus = module->getAudioPorts(&mPorts); if (!mStatus.isOk()) return mStatus; mStatus = module->getAudioRoutes(&mRoutes); if (!mStatus.isOk()) return mStatus; if (port.flags.getTag() == aidl::android::media::audio::common::AudioIoFlags::Tag::input) { mConnectedExternalSourceDevicePorts.erase(port.id); } else { mConnectedExternalSinkDevicePorts.erase(port.id); } return mStatus; } bool ModuleConfig::isMmapSupported() const { const std::vector<AudioPort> mmapOutMixPorts = getMmapOutMixPorts(false /*attachedOnly*/, false /*singlePort*/); getMmapOutMixPorts(false /*connectedOnly*/, false /*singlePort*/); const std::vector<AudioPort> mmapInMixPorts = getMmapInMixPorts(false /*attachedOnly*/, false /*singlePort*/); getMmapInMixPorts(false /*connectedOnly*/, false /*singlePort*/); return !mmapOutMixPorts.empty() || !mmapInMixPorts.empty(); }