AudioPolicyService.cpp revision fba182ce91b43117a452a572a72f29e4b497ea30
190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)/*
290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) * Copyright (C) 2009 The Android Open Source Project
390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) *
490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) * Licensed under the Apache License, Version 2.0 (the "License");
5424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles) * you may not use this file except in compliance with the License.
690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) * You may obtain a copy of the License at
790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) *
890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) *      http://www.apache.org/licenses/LICENSE-2.0
990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) *
1090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) * Unless required by applicable law or agreed to in writing, software
1190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) * distributed under the License is distributed on an "AS IS" BASIS,
1290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) * See the License for the specific language governing permissions and
1490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) * limitations under the License.
1590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) */
1690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
1790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#define LOG_TAG "AudioPolicyService"
1890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)//#define LOG_NDEBUG 0
1990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
20424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)#include "Configuration.h"
2190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#undef __STRICT_ANSI__
2290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#define __STDINT_LIMITS
2390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#define __STDC_LIMIT_MACROS
24424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)#include <stdint.h>
25424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)
2690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include <sys/time.h>
2790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include <binder/IServiceManager.h>
2890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include <utils/Log.h>
2990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include <cutils/properties.h>
30424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)#include <binder/IPCThreadState.h>
3190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include <utils/String16.h>
3290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include <utils/threads.h>
3390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include "AudioPolicyService.h"
3490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include "ServiceUtilities.h"
35424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)#include <hardware_legacy/power.h>
3690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include <media/AudioEffect.h>
3790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include <media/EffectsFactoryApi.h>
3890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
3990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include <hardware/hardware.h>
40424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)#include <system/audio.h>
4190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include <system/audio_policy.h>
4290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include <hardware/audio_policy.h>
4390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
4490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)namespace android {
4590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
4690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)static const char kDeadlockedString[] = "AudioPolicyService may be deadlocked\n";
4790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)static const char kCmdDeadlockedString[] = "AudioPolicyService command thread may be deadlocked\n";
4890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
4990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)static const int kDumpLockRetries = 50;
5068043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)static const int kDumpLockSleepUs = 20000;
5190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
5290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)static const nsecs_t kAudioCommandTimeoutNs = seconds(3); // 3 seconds
5390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
5490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)namespace {
5568043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)    extern struct audio_policy_service_ops aps_ops;
5690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)};
5790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
5868043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)// ----------------------------------------------------------------------------
5990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
6090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)AudioPolicyService::AudioPolicyService()
61424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)    : BnAudioPolicyService(), mpAudioPolicyDev(NULL), mpAudioPolicy(NULL),
6290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      mAudioPolicyManager(NULL), mAudioPolicyClient(NULL), mPhoneState(AUDIO_MODE_INVALID)
6390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles){
6490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)}
6590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
6690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)void AudioPolicyService::onFirstRef()
6790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles){
6890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    char value[PROPERTY_VALUE_MAX];
6990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    const struct hw_module_t *module;
7090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    int forced_val;
7190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    int rc;
7290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
7390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    {
7490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        Mutex::Autolock _l(mLock);
7590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
7690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        // start tone playback thread
7790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        mTonePlaybackThread = new AudioCommandThread(String8("ApmTone"), this);
7890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        // start audio commands thread
7990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        mAudioCommandThread = new AudioCommandThread(String8("ApmAudio"), this);
8090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        // start output activity command thread
81424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)        mOutputCommandThread = new AudioCommandThread(String8("ApmOutput"), this);
82424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)
8390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#ifdef USE_LEGACY_AUDIO_POLICY
8490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        ALOGI("AudioPolicyService CSTOR in legacy mode");
8590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
8690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        /* instantiate the audio policy manager */
87424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)        rc = hw_get_module(AUDIO_POLICY_HARDWARE_MODULE_ID, &module);
8890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        if (rc) {
8990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)            return;
9090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        }
91424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)        rc = audio_policy_dev_open(module, &mpAudioPolicyDev);
9290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        ALOGE_IF(rc, "couldn't open audio policy device (%s)", strerror(-rc));
93424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)        if (rc) {
9490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)            return;
9590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        }
9690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
97        rc = mpAudioPolicyDev->create_audio_policy(mpAudioPolicyDev, &aps_ops, this,
98                                                   &mpAudioPolicy);
99        ALOGE_IF(rc, "couldn't create audio policy (%s)", strerror(-rc));
100        if (rc) {
101            return;
102        }
103
104        rc = mpAudioPolicy->init_check(mpAudioPolicy);
105        ALOGE_IF(rc, "couldn't init_check the audio policy (%s)", strerror(-rc));
106        if (rc) {
107            return;
108        }
109        ALOGI("Loaded audio policy from %s (%s)", module->name, module->id);
110#else
111        ALOGI("AudioPolicyService CSTOR in new mode");
112
113        mAudioPolicyClient = new AudioPolicyClient(this);
114        mAudioPolicyManager = createAudioPolicyManager(mAudioPolicyClient);
115#endif
116    }
117    // load audio processing modules
118    sp<AudioPolicyEffects>audioPolicyEffects = new AudioPolicyEffects();
119    {
120        Mutex::Autolock _l(mLock);
121        mAudioPolicyEffects = audioPolicyEffects;
122    }
123}
124
125AudioPolicyService::~AudioPolicyService()
126{
127    mTonePlaybackThread->exit();
128    mAudioCommandThread->exit();
129    mOutputCommandThread->exit();
130
131#ifdef USE_LEGACY_AUDIO_POLICY
132    if (mpAudioPolicy != NULL && mpAudioPolicyDev != NULL) {
133        mpAudioPolicyDev->destroy_audio_policy(mpAudioPolicyDev, mpAudioPolicy);
134    }
135    if (mpAudioPolicyDev != NULL) {
136        audio_policy_dev_close(mpAudioPolicyDev);
137    }
138#else
139    destroyAudioPolicyManager(mAudioPolicyManager);
140    delete mAudioPolicyClient;
141#endif
142
143    mNotificationClients.clear();
144    mAudioPolicyEffects.clear();
145}
146
147// A notification client is always registered by AudioSystem when the client process
148// connects to AudioPolicyService.
149void AudioPolicyService::registerClient(const sp<IAudioPolicyServiceClient>& client)
150{
151
152    Mutex::Autolock _l(mLock);
153
154    uid_t uid = IPCThreadState::self()->getCallingUid();
155    if (mNotificationClients.indexOfKey(uid) < 0) {
156        sp<NotificationClient> notificationClient = new NotificationClient(this,
157                                                                           client,
158                                                                           uid);
159        ALOGV("registerClient() client %p, uid %d", client.get(), uid);
160
161        mNotificationClients.add(uid, notificationClient);
162
163        sp<IBinder> binder = client->asBinder();
164        binder->linkToDeath(notificationClient);
165    }
166}
167
168// removeNotificationClient() is called when the client process dies.
169void AudioPolicyService::removeNotificationClient(uid_t uid)
170{
171    Mutex::Autolock _l(mLock);
172
173    mNotificationClients.removeItem(uid);
174
175#ifndef USE_LEGACY_AUDIO_POLICY
176        if (mAudioPolicyManager) {
177            mAudioPolicyManager->clearAudioPatches(uid);
178        }
179#endif
180}
181
182void AudioPolicyService::onAudioPortListUpdate()
183{
184    mOutputCommandThread->updateAudioPortListCommand();
185}
186
187void AudioPolicyService::doOnAudioPortListUpdate()
188{
189    Mutex::Autolock _l(mLock);
190    for (size_t i = 0; i < mNotificationClients.size(); i++) {
191        mNotificationClients.valueAt(i)->onAudioPortListUpdate();
192    }
193}
194
195void AudioPolicyService::onAudioPatchListUpdate()
196{
197    mOutputCommandThread->updateAudioPatchListCommand();
198}
199
200status_t AudioPolicyService::clientCreateAudioPatch(const struct audio_patch *patch,
201                                                audio_patch_handle_t *handle,
202                                                int delayMs)
203{
204    return mAudioCommandThread->createAudioPatchCommand(patch, handle, delayMs);
205}
206
207status_t AudioPolicyService::clientReleaseAudioPatch(audio_patch_handle_t handle,
208                                                 int delayMs)
209{
210    return mAudioCommandThread->releaseAudioPatchCommand(handle, delayMs);
211}
212
213void AudioPolicyService::doOnAudioPatchListUpdate()
214{
215    Mutex::Autolock _l(mLock);
216    for (size_t i = 0; i < mNotificationClients.size(); i++) {
217        mNotificationClients.valueAt(i)->onAudioPatchListUpdate();
218    }
219}
220
221status_t AudioPolicyService::clientSetAudioPortConfig(const struct audio_port_config *config,
222                                                      int delayMs)
223{
224    return mAudioCommandThread->setAudioPortConfigCommand(config, delayMs);
225}
226
227AudioPolicyService::NotificationClient::NotificationClient(const sp<AudioPolicyService>& service,
228                                                     const sp<IAudioPolicyServiceClient>& client,
229                                                     uid_t uid)
230    : mService(service), mUid(uid), mAudioPolicyServiceClient(client)
231{
232}
233
234AudioPolicyService::NotificationClient::~NotificationClient()
235{
236}
237
238void AudioPolicyService::NotificationClient::binderDied(const wp<IBinder>& who __unused)
239{
240    sp<NotificationClient> keep(this);
241    sp<AudioPolicyService> service = mService.promote();
242    if (service != 0) {
243        service->removeNotificationClient(mUid);
244    }
245}
246
247void AudioPolicyService::NotificationClient::onAudioPortListUpdate()
248{
249    if (mAudioPolicyServiceClient != 0) {
250        mAudioPolicyServiceClient->onAudioPortListUpdate();
251    }
252}
253
254void AudioPolicyService::NotificationClient::onAudioPatchListUpdate()
255{
256    if (mAudioPolicyServiceClient != 0) {
257        mAudioPolicyServiceClient->onAudioPatchListUpdate();
258    }
259}
260
261void AudioPolicyService::binderDied(const wp<IBinder>& who) {
262    ALOGW("binderDied() %p, calling pid %d", who.unsafe_get(),
263            IPCThreadState::self()->getCallingPid());
264}
265
266static bool tryLock(Mutex& mutex)
267{
268    bool locked = false;
269    for (int i = 0; i < kDumpLockRetries; ++i) {
270        if (mutex.tryLock() == NO_ERROR) {
271            locked = true;
272            break;
273        }
274        usleep(kDumpLockSleepUs);
275    }
276    return locked;
277}
278
279status_t AudioPolicyService::dumpInternals(int fd)
280{
281    const size_t SIZE = 256;
282    char buffer[SIZE];
283    String8 result;
284
285#ifdef USE_LEGACY_AUDIO_POLICY
286    snprintf(buffer, SIZE, "PolicyManager Interface: %p\n", mpAudioPolicy);
287#else
288    snprintf(buffer, SIZE, "AudioPolicyManager: %p\n", mAudioPolicyManager);
289#endif
290    result.append(buffer);
291    snprintf(buffer, SIZE, "Command Thread: %p\n", mAudioCommandThread.get());
292    result.append(buffer);
293    snprintf(buffer, SIZE, "Tones Thread: %p\n", mTonePlaybackThread.get());
294    result.append(buffer);
295
296    write(fd, result.string(), result.size());
297    return NO_ERROR;
298}
299
300status_t AudioPolicyService::dump(int fd, const Vector<String16>& args __unused)
301{
302    if (!dumpAllowed()) {
303        dumpPermissionDenial(fd);
304    } else {
305        bool locked = tryLock(mLock);
306        if (!locked) {
307            String8 result(kDeadlockedString);
308            write(fd, result.string(), result.size());
309        }
310
311        dumpInternals(fd);
312        if (mAudioCommandThread != 0) {
313            mAudioCommandThread->dump(fd);
314        }
315        if (mTonePlaybackThread != 0) {
316            mTonePlaybackThread->dump(fd);
317        }
318
319#ifdef USE_LEGACY_AUDIO_POLICY
320        if (mpAudioPolicy) {
321            mpAudioPolicy->dump(mpAudioPolicy, fd);
322        }
323#else
324        if (mAudioPolicyManager) {
325            mAudioPolicyManager->dump(fd);
326        }
327#endif
328
329        if (locked) mLock.unlock();
330    }
331    return NO_ERROR;
332}
333
334status_t AudioPolicyService::dumpPermissionDenial(int fd)
335{
336    const size_t SIZE = 256;
337    char buffer[SIZE];
338    String8 result;
339    snprintf(buffer, SIZE, "Permission Denial: "
340            "can't dump AudioPolicyService from pid=%d, uid=%d\n",
341            IPCThreadState::self()->getCallingPid(),
342            IPCThreadState::self()->getCallingUid());
343    result.append(buffer);
344    write(fd, result.string(), result.size());
345    return NO_ERROR;
346}
347
348status_t AudioPolicyService::onTransact(
349        uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
350{
351    return BnAudioPolicyService::onTransact(code, data, reply, flags);
352}
353
354
355// -----------  AudioPolicyService::AudioCommandThread implementation ----------
356
357AudioPolicyService::AudioCommandThread::AudioCommandThread(String8 name,
358                                                           const wp<AudioPolicyService>& service)
359    : Thread(false), mName(name), mService(service)
360{
361    mpToneGenerator = NULL;
362}
363
364
365AudioPolicyService::AudioCommandThread::~AudioCommandThread()
366{
367    if (!mAudioCommands.isEmpty()) {
368        release_wake_lock(mName.string());
369    }
370    mAudioCommands.clear();
371    delete mpToneGenerator;
372}
373
374void AudioPolicyService::AudioCommandThread::onFirstRef()
375{
376    run(mName.string(), ANDROID_PRIORITY_AUDIO);
377}
378
379bool AudioPolicyService::AudioCommandThread::threadLoop()
380{
381    nsecs_t waitTime = INT64_MAX;
382
383    mLock.lock();
384    while (!exitPending())
385    {
386        sp<AudioPolicyService> svc;
387        while (!mAudioCommands.isEmpty() && !exitPending()) {
388            nsecs_t curTime = systemTime();
389            // commands are sorted by increasing time stamp: execute them from index 0 and up
390            if (mAudioCommands[0]->mTime <= curTime) {
391                sp<AudioCommand> command = mAudioCommands[0];
392                mAudioCommands.removeAt(0);
393                mLastCommand = command;
394
395                switch (command->mCommand) {
396                case START_TONE: {
397                    mLock.unlock();
398                    ToneData *data = (ToneData *)command->mParam.get();
399                    ALOGV("AudioCommandThread() processing start tone %d on stream %d",
400                            data->mType, data->mStream);
401                    delete mpToneGenerator;
402                    mpToneGenerator = new ToneGenerator(data->mStream, 1.0);
403                    mpToneGenerator->startTone(data->mType);
404                    mLock.lock();
405                    }break;
406                case STOP_TONE: {
407                    mLock.unlock();
408                    ALOGV("AudioCommandThread() processing stop tone");
409                    if (mpToneGenerator != NULL) {
410                        mpToneGenerator->stopTone();
411                        delete mpToneGenerator;
412                        mpToneGenerator = NULL;
413                    }
414                    mLock.lock();
415                    }break;
416                case SET_VOLUME: {
417                    VolumeData *data = (VolumeData *)command->mParam.get();
418                    ALOGV("AudioCommandThread() processing set volume stream %d, \
419                            volume %f, output %d", data->mStream, data->mVolume, data->mIO);
420                    command->mStatus = AudioSystem::setStreamVolume(data->mStream,
421                                                                    data->mVolume,
422                                                                    data->mIO);
423                    }break;
424                case SET_PARAMETERS: {
425                    ParametersData *data = (ParametersData *)command->mParam.get();
426                    ALOGV("AudioCommandThread() processing set parameters string %s, io %d",
427                            data->mKeyValuePairs.string(), data->mIO);
428                    command->mStatus = AudioSystem::setParameters(data->mIO, data->mKeyValuePairs);
429                    }break;
430                case SET_VOICE_VOLUME: {
431                    VoiceVolumeData *data = (VoiceVolumeData *)command->mParam.get();
432                    ALOGV("AudioCommandThread() processing set voice volume volume %f",
433                            data->mVolume);
434                    command->mStatus = AudioSystem::setVoiceVolume(data->mVolume);
435                    }break;
436                case STOP_OUTPUT: {
437                    StopOutputData *data = (StopOutputData *)command->mParam.get();
438                    ALOGV("AudioCommandThread() processing stop output %d",
439                            data->mIO);
440                    svc = mService.promote();
441                    if (svc == 0) {
442                        break;
443                    }
444                    mLock.unlock();
445                    svc->doStopOutput(data->mIO, data->mStream, data->mSession);
446                    mLock.lock();
447                    }break;
448                case RELEASE_OUTPUT: {
449                    ReleaseOutputData *data = (ReleaseOutputData *)command->mParam.get();
450                    ALOGV("AudioCommandThread() processing release output %d",
451                            data->mIO);
452                    svc = mService.promote();
453                    if (svc == 0) {
454                        break;
455                    }
456                    mLock.unlock();
457                    svc->doReleaseOutput(data->mIO);
458                    mLock.lock();
459                    }break;
460                case CREATE_AUDIO_PATCH: {
461                    CreateAudioPatchData *data = (CreateAudioPatchData *)command->mParam.get();
462                    ALOGV("AudioCommandThread() processing create audio patch");
463                    sp<IAudioFlinger> af = AudioSystem::get_audio_flinger();
464                    if (af == 0) {
465                        command->mStatus = PERMISSION_DENIED;
466                    } else {
467                        command->mStatus = af->createAudioPatch(&data->mPatch, &data->mHandle);
468                    }
469                    } break;
470                case RELEASE_AUDIO_PATCH: {
471                    ReleaseAudioPatchData *data = (ReleaseAudioPatchData *)command->mParam.get();
472                    ALOGV("AudioCommandThread() processing release audio patch");
473                    sp<IAudioFlinger> af = AudioSystem::get_audio_flinger();
474                    if (af == 0) {
475                        command->mStatus = PERMISSION_DENIED;
476                    } else {
477                        command->mStatus = af->releaseAudioPatch(data->mHandle);
478                    }
479                    } break;
480                case UPDATE_AUDIOPORT_LIST: {
481                    ALOGV("AudioCommandThread() processing update audio port list");
482                    svc = mService.promote();
483                    if (svc == 0) {
484                        break;
485                    }
486                    mLock.unlock();
487                    svc->doOnAudioPortListUpdate();
488                    mLock.lock();
489                    }break;
490                case UPDATE_AUDIOPATCH_LIST: {
491                    ALOGV("AudioCommandThread() processing update audio patch list");
492                    svc = mService.promote();
493                    if (svc == 0) {
494                        break;
495                    }
496                    mLock.unlock();
497                    svc->doOnAudioPatchListUpdate();
498                    mLock.lock();
499                    }break;
500                case SET_AUDIOPORT_CONFIG: {
501                    SetAudioPortConfigData *data = (SetAudioPortConfigData *)command->mParam.get();
502                    ALOGV("AudioCommandThread() processing set port config");
503                    sp<IAudioFlinger> af = AudioSystem::get_audio_flinger();
504                    if (af == 0) {
505                        command->mStatus = PERMISSION_DENIED;
506                    } else {
507                        command->mStatus = af->setAudioPortConfig(&data->mConfig);
508                    }
509                    } break;
510                default:
511                    ALOGW("AudioCommandThread() unknown command %d", command->mCommand);
512                }
513                {
514                    Mutex::Autolock _l(command->mLock);
515                    if (command->mWaitStatus) {
516                        command->mWaitStatus = false;
517                        command->mCond.signal();
518                    }
519                }
520                waitTime = INT64_MAX;
521            } else {
522                waitTime = mAudioCommands[0]->mTime - curTime;
523                break;
524            }
525        }
526        // release mLock before releasing strong reference on the service as
527        // AudioPolicyService destructor calls AudioCommandThread::exit() which acquires mLock.
528        mLock.unlock();
529        svc.clear();
530        mLock.lock();
531        if (!exitPending() && mAudioCommands.isEmpty()) {
532            // release delayed commands wake lock
533            release_wake_lock(mName.string());
534            ALOGV("AudioCommandThread() going to sleep");
535            mWaitWorkCV.waitRelative(mLock, waitTime);
536            ALOGV("AudioCommandThread() waking up");
537        }
538    }
539    // release delayed commands wake lock before quitting
540    if (!mAudioCommands.isEmpty()) {
541        release_wake_lock(mName.string());
542    }
543    mLock.unlock();
544    return false;
545}
546
547status_t AudioPolicyService::AudioCommandThread::dump(int fd)
548{
549    const size_t SIZE = 256;
550    char buffer[SIZE];
551    String8 result;
552
553    snprintf(buffer, SIZE, "AudioCommandThread %p Dump\n", this);
554    result.append(buffer);
555    write(fd, result.string(), result.size());
556
557    bool locked = tryLock(mLock);
558    if (!locked) {
559        String8 result2(kCmdDeadlockedString);
560        write(fd, result2.string(), result2.size());
561    }
562
563    snprintf(buffer, SIZE, "- Commands:\n");
564    result = String8(buffer);
565    result.append("   Command Time        Wait pParam\n");
566    for (size_t i = 0; i < mAudioCommands.size(); i++) {
567        mAudioCommands[i]->dump(buffer, SIZE);
568        result.append(buffer);
569    }
570    result.append("  Last Command\n");
571    if (mLastCommand != 0) {
572        mLastCommand->dump(buffer, SIZE);
573        result.append(buffer);
574    } else {
575        result.append("     none\n");
576    }
577
578    write(fd, result.string(), result.size());
579
580    if (locked) mLock.unlock();
581
582    return NO_ERROR;
583}
584
585void AudioPolicyService::AudioCommandThread::startToneCommand(ToneGenerator::tone_type type,
586        audio_stream_type_t stream)
587{
588    sp<AudioCommand> command = new AudioCommand();
589    command->mCommand = START_TONE;
590    sp<ToneData> data = new ToneData();
591    data->mType = type;
592    data->mStream = stream;
593    command->mParam = data;
594    ALOGV("AudioCommandThread() adding tone start type %d, stream %d", type, stream);
595    sendCommand(command);
596}
597
598void AudioPolicyService::AudioCommandThread::stopToneCommand()
599{
600    sp<AudioCommand> command = new AudioCommand();
601    command->mCommand = STOP_TONE;
602    ALOGV("AudioCommandThread() adding tone stop");
603    sendCommand(command);
604}
605
606status_t AudioPolicyService::AudioCommandThread::volumeCommand(audio_stream_type_t stream,
607                                                               float volume,
608                                                               audio_io_handle_t output,
609                                                               int delayMs)
610{
611    sp<AudioCommand> command = new AudioCommand();
612    command->mCommand = SET_VOLUME;
613    sp<VolumeData> data = new VolumeData();
614    data->mStream = stream;
615    data->mVolume = volume;
616    data->mIO = output;
617    command->mParam = data;
618    command->mWaitStatus = true;
619    ALOGV("AudioCommandThread() adding set volume stream %d, volume %f, output %d",
620            stream, volume, output);
621    return sendCommand(command, delayMs);
622}
623
624status_t AudioPolicyService::AudioCommandThread::parametersCommand(audio_io_handle_t ioHandle,
625                                                                   const char *keyValuePairs,
626                                                                   int delayMs)
627{
628    sp<AudioCommand> command = new AudioCommand();
629    command->mCommand = SET_PARAMETERS;
630    sp<ParametersData> data = new ParametersData();
631    data->mIO = ioHandle;
632    data->mKeyValuePairs = String8(keyValuePairs);
633    command->mParam = data;
634    command->mWaitStatus = true;
635    ALOGV("AudioCommandThread() adding set parameter string %s, io %d ,delay %d",
636            keyValuePairs, ioHandle, delayMs);
637    return sendCommand(command, delayMs);
638}
639
640status_t AudioPolicyService::AudioCommandThread::voiceVolumeCommand(float volume, int delayMs)
641{
642    sp<AudioCommand> command = new AudioCommand();
643    command->mCommand = SET_VOICE_VOLUME;
644    sp<VoiceVolumeData> data = new VoiceVolumeData();
645    data->mVolume = volume;
646    command->mParam = data;
647    command->mWaitStatus = true;
648    ALOGV("AudioCommandThread() adding set voice volume volume %f", volume);
649    return sendCommand(command, delayMs);
650}
651
652void AudioPolicyService::AudioCommandThread::stopOutputCommand(audio_io_handle_t output,
653                                                               audio_stream_type_t stream,
654                                                               int session)
655{
656    sp<AudioCommand> command = new AudioCommand();
657    command->mCommand = STOP_OUTPUT;
658    sp<StopOutputData> data = new StopOutputData();
659    data->mIO = output;
660    data->mStream = stream;
661    data->mSession = session;
662    command->mParam = data;
663    ALOGV("AudioCommandThread() adding stop output %d", output);
664    sendCommand(command);
665}
666
667void AudioPolicyService::AudioCommandThread::releaseOutputCommand(audio_io_handle_t output)
668{
669    sp<AudioCommand> command = new AudioCommand();
670    command->mCommand = RELEASE_OUTPUT;
671    sp<ReleaseOutputData> data = new ReleaseOutputData();
672    data->mIO = output;
673    command->mParam = data;
674    ALOGV("AudioCommandThread() adding release output %d", output);
675    sendCommand(command);
676}
677
678status_t AudioPolicyService::AudioCommandThread::createAudioPatchCommand(
679                                                const struct audio_patch *patch,
680                                                audio_patch_handle_t *handle,
681                                                int delayMs)
682{
683    status_t status = NO_ERROR;
684
685    sp<AudioCommand> command = new AudioCommand();
686    command->mCommand = CREATE_AUDIO_PATCH;
687    CreateAudioPatchData *data = new CreateAudioPatchData();
688    data->mPatch = *patch;
689    data->mHandle = *handle;
690    command->mParam = data;
691    command->mWaitStatus = true;
692    ALOGV("AudioCommandThread() adding create patch delay %d", delayMs);
693    status = sendCommand(command, delayMs);
694    if (status == NO_ERROR) {
695        *handle = data->mHandle;
696    }
697    return status;
698}
699
700status_t AudioPolicyService::AudioCommandThread::releaseAudioPatchCommand(audio_patch_handle_t handle,
701                                                 int delayMs)
702{
703    sp<AudioCommand> command = new AudioCommand();
704    command->mCommand = RELEASE_AUDIO_PATCH;
705    ReleaseAudioPatchData *data = new ReleaseAudioPatchData();
706    data->mHandle = handle;
707    command->mParam = data;
708    command->mWaitStatus = true;
709    ALOGV("AudioCommandThread() adding release patch delay %d", delayMs);
710    return sendCommand(command, delayMs);
711}
712
713void AudioPolicyService::AudioCommandThread::updateAudioPortListCommand()
714{
715    sp<AudioCommand> command = new AudioCommand();
716    command->mCommand = UPDATE_AUDIOPORT_LIST;
717    ALOGV("AudioCommandThread() adding update audio port list");
718    sendCommand(command);
719}
720
721void AudioPolicyService::AudioCommandThread::updateAudioPatchListCommand()
722{
723    sp<AudioCommand>command = new AudioCommand();
724    command->mCommand = UPDATE_AUDIOPATCH_LIST;
725    ALOGV("AudioCommandThread() adding update audio patch list");
726    sendCommand(command);
727}
728
729status_t AudioPolicyService::AudioCommandThread::setAudioPortConfigCommand(
730                                            const struct audio_port_config *config, int delayMs)
731{
732    sp<AudioCommand> command = new AudioCommand();
733    command->mCommand = SET_AUDIOPORT_CONFIG;
734    SetAudioPortConfigData *data = new SetAudioPortConfigData();
735    data->mConfig = *config;
736    command->mParam = data;
737    command->mWaitStatus = true;
738    ALOGV("AudioCommandThread() adding set port config delay %d", delayMs);
739    return sendCommand(command, delayMs);
740}
741
742status_t AudioPolicyService::AudioCommandThread::sendCommand(sp<AudioCommand>& command, int delayMs)
743{
744    {
745        Mutex::Autolock _l(mLock);
746        insertCommand_l(command, delayMs);
747        mWaitWorkCV.signal();
748    }
749    Mutex::Autolock _l(command->mLock);
750    while (command->mWaitStatus) {
751        nsecs_t timeOutNs = kAudioCommandTimeoutNs + milliseconds(delayMs);
752        if (command->mCond.waitRelative(command->mLock, timeOutNs) != NO_ERROR) {
753            command->mStatus = TIMED_OUT;
754            command->mWaitStatus = false;
755        }
756    }
757    return command->mStatus;
758}
759
760// insertCommand_l() must be called with mLock held
761void AudioPolicyService::AudioCommandThread::insertCommand_l(sp<AudioCommand>& command, int delayMs)
762{
763    ssize_t i;  // not size_t because i will count down to -1
764    Vector < sp<AudioCommand> > removedCommands;
765    command->mTime = systemTime() + milliseconds(delayMs);
766
767    // acquire wake lock to make sure delayed commands are processed
768    if (mAudioCommands.isEmpty()) {
769        acquire_wake_lock(PARTIAL_WAKE_LOCK, mName.string());
770    }
771
772    // check same pending commands with later time stamps and eliminate them
773    for (i = mAudioCommands.size()-1; i >= 0; i--) {
774        sp<AudioCommand> command2 = mAudioCommands[i];
775        // commands are sorted by increasing time stamp: no need to scan the rest of mAudioCommands
776        if (command2->mTime <= command->mTime) break;
777
778        // create audio patch or release audio patch commands are equivalent
779        // with regard to filtering
780        if ((command->mCommand == CREATE_AUDIO_PATCH) ||
781                (command->mCommand == RELEASE_AUDIO_PATCH)) {
782            if ((command2->mCommand != CREATE_AUDIO_PATCH) &&
783                    (command2->mCommand != RELEASE_AUDIO_PATCH)) {
784                continue;
785            }
786        } else if (command2->mCommand != command->mCommand) continue;
787
788        switch (command->mCommand) {
789        case SET_PARAMETERS: {
790            ParametersData *data = (ParametersData *)command->mParam.get();
791            ParametersData *data2 = (ParametersData *)command2->mParam.get();
792            if (data->mIO != data2->mIO) break;
793            ALOGV("Comparing parameter command %s to new command %s",
794                    data2->mKeyValuePairs.string(), data->mKeyValuePairs.string());
795            AudioParameter param = AudioParameter(data->mKeyValuePairs);
796            AudioParameter param2 = AudioParameter(data2->mKeyValuePairs);
797            for (size_t j = 0; j < param.size(); j++) {
798                String8 key;
799                String8 value;
800                param.getAt(j, key, value);
801                for (size_t k = 0; k < param2.size(); k++) {
802                    String8 key2;
803                    String8 value2;
804                    param2.getAt(k, key2, value2);
805                    if (key2 == key) {
806                        param2.remove(key2);
807                        ALOGV("Filtering out parameter %s", key2.string());
808                        break;
809                    }
810                }
811            }
812            // if all keys have been filtered out, remove the command.
813            // otherwise, update the key value pairs
814            if (param2.size() == 0) {
815                removedCommands.add(command2);
816            } else {
817                data2->mKeyValuePairs = param2.toString();
818            }
819            command->mTime = command2->mTime;
820            // force delayMs to non 0 so that code below does not request to wait for
821            // command status as the command is now delayed
822            delayMs = 1;
823        } break;
824
825        case SET_VOLUME: {
826            VolumeData *data = (VolumeData *)command->mParam.get();
827            VolumeData *data2 = (VolumeData *)command2->mParam.get();
828            if (data->mIO != data2->mIO) break;
829            if (data->mStream != data2->mStream) break;
830            ALOGV("Filtering out volume command on output %d for stream %d",
831                    data->mIO, data->mStream);
832            removedCommands.add(command2);
833            command->mTime = command2->mTime;
834            // force delayMs to non 0 so that code below does not request to wait for
835            // command status as the command is now delayed
836            delayMs = 1;
837        } break;
838
839        case CREATE_AUDIO_PATCH:
840        case RELEASE_AUDIO_PATCH: {
841            audio_patch_handle_t handle;
842            if (command->mCommand == CREATE_AUDIO_PATCH) {
843                handle = ((CreateAudioPatchData *)command->mParam.get())->mHandle;
844            } else {
845                handle = ((ReleaseAudioPatchData *)command->mParam.get())->mHandle;
846            }
847            audio_patch_handle_t handle2;
848            if (command2->mCommand == CREATE_AUDIO_PATCH) {
849                handle2 = ((CreateAudioPatchData *)command2->mParam.get())->mHandle;
850            } else {
851                handle2 = ((ReleaseAudioPatchData *)command2->mParam.get())->mHandle;
852            }
853            if (handle != handle2) break;
854            ALOGV("Filtering out %s audio patch command for handle %d",
855                  (command->mCommand == CREATE_AUDIO_PATCH) ? "create" : "release", handle);
856            removedCommands.add(command2);
857            command->mTime = command2->mTime;
858            // force delayMs to non 0 so that code below does not request to wait for
859            // command status as the command is now delayed
860            delayMs = 1;
861        } break;
862
863        case START_TONE:
864        case STOP_TONE:
865        default:
866            break;
867        }
868    }
869
870    // remove filtered commands
871    for (size_t j = 0; j < removedCommands.size(); j++) {
872        // removed commands always have time stamps greater than current command
873        for (size_t k = i + 1; k < mAudioCommands.size(); k++) {
874            if (mAudioCommands[k].get() == removedCommands[j].get()) {
875                ALOGV("suppressing command: %d", mAudioCommands[k]->mCommand);
876                mAudioCommands.removeAt(k);
877                break;
878            }
879        }
880    }
881    removedCommands.clear();
882
883    // Disable wait for status if delay is not 0
884    if (delayMs != 0) {
885        command->mWaitStatus = false;
886    }
887
888    // insert command at the right place according to its time stamp
889    ALOGV("inserting command: %d at index %zd, num commands %zu",
890            command->mCommand, i+1, mAudioCommands.size());
891    mAudioCommands.insertAt(command, i + 1);
892}
893
894void AudioPolicyService::AudioCommandThread::exit()
895{
896    ALOGV("AudioCommandThread::exit");
897    {
898        AutoMutex _l(mLock);
899        requestExit();
900        mWaitWorkCV.signal();
901    }
902    requestExitAndWait();
903}
904
905void AudioPolicyService::AudioCommandThread::AudioCommand::dump(char* buffer, size_t size)
906{
907    snprintf(buffer, size, "   %02d      %06d.%03d  %01u    %p\n",
908            mCommand,
909            (int)ns2s(mTime),
910            (int)ns2ms(mTime)%1000,
911            mWaitStatus,
912            mParam.get());
913}
914
915/******* helpers for the service_ops callbacks defined below *********/
916void AudioPolicyService::setParameters(audio_io_handle_t ioHandle,
917                                       const char *keyValuePairs,
918                                       int delayMs)
919{
920    mAudioCommandThread->parametersCommand(ioHandle, keyValuePairs,
921                                           delayMs);
922}
923
924int AudioPolicyService::setStreamVolume(audio_stream_type_t stream,
925                                        float volume,
926                                        audio_io_handle_t output,
927                                        int delayMs)
928{
929    return (int)mAudioCommandThread->volumeCommand(stream, volume,
930                                                   output, delayMs);
931}
932
933int AudioPolicyService::startTone(audio_policy_tone_t tone,
934                                  audio_stream_type_t stream)
935{
936    if (tone != AUDIO_POLICY_TONE_IN_CALL_NOTIFICATION) {
937        ALOGE("startTone: illegal tone requested (%d)", tone);
938    }
939    if (stream != AUDIO_STREAM_VOICE_CALL) {
940        ALOGE("startTone: illegal stream (%d) requested for tone %d", stream,
941            tone);
942    }
943    mTonePlaybackThread->startToneCommand(ToneGenerator::TONE_SUP_CALL_WAITING,
944                                          AUDIO_STREAM_VOICE_CALL);
945    return 0;
946}
947
948int AudioPolicyService::stopTone()
949{
950    mTonePlaybackThread->stopToneCommand();
951    return 0;
952}
953
954int AudioPolicyService::setVoiceVolume(float volume, int delayMs)
955{
956    return (int)mAudioCommandThread->voiceVolumeCommand(volume, delayMs);
957}
958
959extern "C" {
960audio_module_handle_t aps_load_hw_module(void *service __unused,
961                                             const char *name);
962audio_io_handle_t aps_open_output(void *service __unused,
963                                         audio_devices_t *pDevices,
964                                         uint32_t *pSamplingRate,
965                                         audio_format_t *pFormat,
966                                         audio_channel_mask_t *pChannelMask,
967                                         uint32_t *pLatencyMs,
968                                         audio_output_flags_t flags);
969
970audio_io_handle_t aps_open_output_on_module(void *service __unused,
971                                                   audio_module_handle_t module,
972                                                   audio_devices_t *pDevices,
973                                                   uint32_t *pSamplingRate,
974                                                   audio_format_t *pFormat,
975                                                   audio_channel_mask_t *pChannelMask,
976                                                   uint32_t *pLatencyMs,
977                                                   audio_output_flags_t flags,
978                                                   const audio_offload_info_t *offloadInfo);
979audio_io_handle_t aps_open_dup_output(void *service __unused,
980                                                 audio_io_handle_t output1,
981                                                 audio_io_handle_t output2);
982int aps_close_output(void *service __unused, audio_io_handle_t output);
983int aps_suspend_output(void *service __unused, audio_io_handle_t output);
984int aps_restore_output(void *service __unused, audio_io_handle_t output);
985audio_io_handle_t aps_open_input(void *service __unused,
986                                        audio_devices_t *pDevices,
987                                        uint32_t *pSamplingRate,
988                                        audio_format_t *pFormat,
989                                        audio_channel_mask_t *pChannelMask,
990                                        audio_in_acoustics_t acoustics __unused);
991audio_io_handle_t aps_open_input_on_module(void *service __unused,
992                                                  audio_module_handle_t module,
993                                                  audio_devices_t *pDevices,
994                                                  uint32_t *pSamplingRate,
995                                                  audio_format_t *pFormat,
996                                                  audio_channel_mask_t *pChannelMask);
997int aps_close_input(void *service __unused, audio_io_handle_t input);
998int aps_invalidate_stream(void *service __unused, audio_stream_type_t stream);
999int aps_move_effects(void *service __unused, int session,
1000                                audio_io_handle_t src_output,
1001                                audio_io_handle_t dst_output);
1002char * aps_get_parameters(void *service __unused, audio_io_handle_t io_handle,
1003                                     const char *keys);
1004void aps_set_parameters(void *service, audio_io_handle_t io_handle,
1005                                   const char *kv_pairs, int delay_ms);
1006int aps_set_stream_volume(void *service, audio_stream_type_t stream,
1007                                     float volume, audio_io_handle_t output,
1008                                     int delay_ms);
1009int aps_start_tone(void *service, audio_policy_tone_t tone,
1010                              audio_stream_type_t stream);
1011int aps_stop_tone(void *service);
1012int aps_set_voice_volume(void *service, float volume, int delay_ms);
1013};
1014
1015namespace {
1016    struct audio_policy_service_ops aps_ops = {
1017        .open_output           = aps_open_output,
1018        .open_duplicate_output = aps_open_dup_output,
1019        .close_output          = aps_close_output,
1020        .suspend_output        = aps_suspend_output,
1021        .restore_output        = aps_restore_output,
1022        .open_input            = aps_open_input,
1023        .close_input           = aps_close_input,
1024        .set_stream_volume     = aps_set_stream_volume,
1025        .invalidate_stream     = aps_invalidate_stream,
1026        .set_parameters        = aps_set_parameters,
1027        .get_parameters        = aps_get_parameters,
1028        .start_tone            = aps_start_tone,
1029        .stop_tone             = aps_stop_tone,
1030        .set_voice_volume      = aps_set_voice_volume,
1031        .move_effects          = aps_move_effects,
1032        .load_hw_module        = aps_load_hw_module,
1033        .open_output_on_module = aps_open_output_on_module,
1034        .open_input_on_module  = aps_open_input_on_module,
1035    };
1036}; // namespace <unnamed>
1037
1038}; // namespace android
1039