1 /* 2 ** 3 ** Copyright 2019, The Android Open Source Project 4 ** 5 ** Licensed under the Apache License, Version 2.0 (the "License"); 6 ** you may not use this file except in compliance with the License. 7 ** You may obtain a copy of the License at 8 ** 9 ** http://www.apache.org/licenses/LICENSE-2.0 10 ** 11 ** Unless required by applicable law or agreed to in writing, software 12 ** distributed under the License is distributed on an "AS IS" BASIS, 13 ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 ** See the License for the specific language governing permissions and 15 ** limitations under the License. 16 */ 17 18 #ifndef INCLUDING_FROM_AUDIOFLINGER_H 19 #error This header file should only be included from AudioFlinger.h 20 #endif 21 22 // DeviceEffectManager is concealed within AudioFlinger, their lifetimes are the same. 23 class DeviceEffectManager { 24 public: DeviceEffectManager(AudioFlinger * audioFlinger)25 explicit DeviceEffectManager(AudioFlinger* audioFlinger) 26 : mCommandThread(new CommandThread(*this)), mAudioFlinger(*audioFlinger), 27 mMyCallback(new DeviceEffectManagerCallback(this)) {} 28 ~DeviceEffectManager()29 ~DeviceEffectManager() { 30 mCommandThread->exit(); 31 } 32 33 sp<EffectHandle> createEffect_l(effect_descriptor_t *descriptor, 34 const AudioDeviceTypeAddr& device, 35 const sp<AudioFlinger::Client>& client, 36 const sp<IEffectClient>& effectClient, 37 const std::map<audio_patch_handle_t, PatchPanel::Patch>& patches, 38 int *enabled, 39 status_t *status); 40 void createAudioPatch(audio_patch_handle_t handle, const PatchPanel::Patch& patch); 41 void releaseAudioPatch(audio_patch_handle_t handle); 42 43 size_t removeEffect(const sp<DeviceEffectProxy>& effect); 44 status_t createEffectHal(const effect_uuid_t *pEffectUuid, 45 int32_t sessionId, int32_t deviceId, 46 sp<EffectHalInterface> *effect); addEffectToHal(audio_port_handle_t deviceId,audio_module_handle_t hwModuleId,sp<EffectHalInterface> effect)47 status_t addEffectToHal(audio_port_handle_t deviceId, audio_module_handle_t hwModuleId, 48 sp<EffectHalInterface> effect) { 49 return mAudioFlinger.addEffectToHal(deviceId, hwModuleId, effect); 50 }; removeEffectFromHal(audio_port_handle_t deviceId,audio_module_handle_t hwModuleId,sp<EffectHalInterface> effect)51 status_t removeEffectFromHal(audio_port_handle_t deviceId, audio_module_handle_t hwModuleId, 52 sp<EffectHalInterface> effect) { 53 return mAudioFlinger.removeEffectFromHal(deviceId, hwModuleId, effect); 54 }; 55 audioFlinger()56 AudioFlinger& audioFlinger() const { return mAudioFlinger; } 57 58 void dump(int fd); 59 60 private: 61 62 // Thread to execute create and release patch commands asynchronously. This is needed because 63 // PatchPanel::createAudioPatch and releaseAudioPatch are executed from audio policy service 64 // with mutex locked and effect management requires to call back into audio policy service 65 class Command; 66 class CommandThread : public Thread { 67 public: 68 69 enum { 70 CREATE_AUDIO_PATCH, 71 RELEASE_AUDIO_PATCH, 72 }; 73 CommandThread(DeviceEffectManager & manager)74 CommandThread(DeviceEffectManager& manager) 75 : Thread(false), mManager(manager) {} 76 ~CommandThread() override; 77 78 // Thread virtuals 79 void onFirstRef() override; 80 bool threadLoop() override; 81 82 void exit(); 83 84 void createAudioPatchCommand(audio_patch_handle_t handle, 85 const PatchPanel::Patch& patch); 86 void releaseAudioPatchCommand(audio_patch_handle_t handle); 87 88 private: 89 class CommandData; 90 91 // descriptor for requested tone playback event 92 class Command: public RefBase { 93 public: 94 Command() = default; Command(int command,sp<CommandData> data)95 Command(int command, sp<CommandData> data) 96 : mCommand(command), mData(data) {} 97 98 int mCommand = -1; 99 sp<CommandData> mData; 100 }; 101 102 class CommandData: public RefBase { 103 public: 104 virtual ~CommandData() = default; 105 }; 106 107 class CreateAudioPatchData : public CommandData { 108 public: CreateAudioPatchData(audio_patch_handle_t handle,const PatchPanel::Patch & patch)109 CreateAudioPatchData(audio_patch_handle_t handle, const PatchPanel::Patch& patch) 110 : mHandle(handle), mPatch(patch) {} 111 112 audio_patch_handle_t mHandle; 113 const PatchPanel::Patch mPatch; 114 }; 115 116 class ReleaseAudioPatchData : public CommandData { 117 public: ReleaseAudioPatchData(audio_patch_handle_t handle)118 ReleaseAudioPatchData(audio_patch_handle_t handle) 119 : mHandle(handle) {} 120 121 audio_patch_handle_t mHandle; 122 }; 123 124 void sendCommand(sp<Command> command); 125 126 Mutex mLock; 127 Condition mWaitWorkCV; 128 std::deque <sp<Command>> mCommands; // list of pending commands 129 DeviceEffectManager& mManager; 130 }; 131 132 void onCreateAudioPatch(audio_patch_handle_t handle, const PatchPanel::Patch& patch); 133 void onReleaseAudioPatch(audio_patch_handle_t handle); 134 135 status_t checkEffectCompatibility(const effect_descriptor_t *desc); 136 137 Mutex mLock; 138 sp<CommandThread> mCommandThread; 139 AudioFlinger &mAudioFlinger; 140 const sp<DeviceEffectManagerCallback> mMyCallback; 141 std::map<AudioDeviceTypeAddr, sp<DeviceEffectProxy>> mDeviceEffects; 142 }; 143 144 class DeviceEffectManagerCallback : public EffectCallbackInterface { 145 public: DeviceEffectManagerCallback(DeviceEffectManager * manager)146 DeviceEffectManagerCallback(DeviceEffectManager *manager) 147 : mManager(*manager) {} 148 createEffectHal(const effect_uuid_t * pEffectUuid,int32_t sessionId,int32_t deviceId,sp<EffectHalInterface> * effect)149 status_t createEffectHal(const effect_uuid_t *pEffectUuid, 150 int32_t sessionId, int32_t deviceId, 151 sp<EffectHalInterface> *effect) override { 152 return mManager.createEffectHal(pEffectUuid, sessionId, deviceId, effect); 153 } allocateHalBuffer(size_t size __unused,sp<EffectBufferHalInterface> * buffer __unused)154 status_t allocateHalBuffer(size_t size __unused, 155 sp<EffectBufferHalInterface>* buffer __unused) override { return NO_ERROR; } updateOrphanEffectChains(const sp<EffectBase> & effect __unused)156 bool updateOrphanEffectChains(const sp<EffectBase>& effect __unused) override { return false; } 157 io()158 audio_io_handle_t io() const override { return AUDIO_IO_HANDLE_NONE; } isOutput()159 bool isOutput() const override { return false; } isOffload()160 bool isOffload() const override { return false; } isOffloadOrDirect()161 bool isOffloadOrDirect() const override { return false; } isOffloadOrMmap()162 bool isOffloadOrMmap() const override { return false; } 163 sampleRate()164 uint32_t sampleRate() const override { return 0; } channelMask()165 audio_channel_mask_t channelMask() const override { return AUDIO_CHANNEL_NONE; } channelCount()166 uint32_t channelCount() const override { return 0; } frameCount()167 size_t frameCount() const override { return 0; } latency()168 uint32_t latency() const override { return 0; } 169 addEffectToHal(sp<EffectHalInterface> effect __unused)170 status_t addEffectToHal(sp<EffectHalInterface> effect __unused) override { 171 return NO_ERROR; 172 } removeEffectFromHal(sp<EffectHalInterface> effect __unused)173 status_t removeEffectFromHal(sp<EffectHalInterface> effect __unused) override { 174 return NO_ERROR; 175 } 176 177 bool disconnectEffectHandle(EffectHandle *handle, bool unpinIfLast) override; setVolumeForOutput(float left __unused,float right __unused)178 void setVolumeForOutput(float left __unused, float right __unused) const override {} 179 180 // check if effects should be suspended or restored when a given effect is enable or disabled checkSuspendOnEffectEnabled(const sp<EffectBase> & effect __unused,bool enabled __unused,bool threadLocked __unused)181 void checkSuspendOnEffectEnabled(const sp<EffectBase>& effect __unused, 182 bool enabled __unused, bool threadLocked __unused) override {} resetVolume()183 void resetVolume() override {} strategy()184 uint32_t strategy() const override { return 0; } activeTrackCnt()185 int32_t activeTrackCnt() const override { return 0; } onEffectEnable(const sp<EffectBase> & effect __unused)186 void onEffectEnable(const sp<EffectBase>& effect __unused) override {} onEffectDisable(const sp<EffectBase> & effect __unused)187 void onEffectDisable(const sp<EffectBase>& effect __unused) override {} 188 chain()189 wp<EffectChain> chain() const override { return nullptr; } 190 newEffectId()191 int newEffectId() { return mManager.audioFlinger().nextUniqueId(AUDIO_UNIQUE_ID_USE_EFFECT); } 192 addEffectToHal(audio_port_handle_t deviceId,audio_module_handle_t hwModuleId,sp<EffectHalInterface> effect)193 status_t addEffectToHal(audio_port_handle_t deviceId, 194 audio_module_handle_t hwModuleId, sp<EffectHalInterface> effect) { 195 return mManager.addEffectToHal(deviceId, hwModuleId, effect); 196 } removeEffectFromHal(audio_port_handle_t deviceId,audio_module_handle_t hwModuleId,sp<EffectHalInterface> effect)197 status_t removeEffectFromHal(audio_port_handle_t deviceId, 198 audio_module_handle_t hwModuleId, sp<EffectHalInterface> effect) { 199 return mManager.removeEffectFromHal(deviceId, hwModuleId, effect); 200 } 201 private: 202 DeviceEffectManager& mManager; 203 }; 204