AudioPolicyService.cpp revision a553c25b33c99b345cf1c8688f8df0ed8df14e5a
1a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent/*
2a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent * Copyright (C) 2009 The Android Open Source Project
3a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent *
4a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent * Licensed under the Apache License, Version 2.0 (the "License");
5a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent * you may not use this file except in compliance with the License.
6a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent * You may obtain a copy of the License at
7a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent *
8a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent *      http://www.apache.org/licenses/LICENSE-2.0
9a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent *
10a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent * Unless required by applicable law or agreed to in writing, software
11a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent * distributed under the License is distributed on an "AS IS" BASIS,
12a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent * See the License for the specific language governing permissions and
14a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent * limitations under the License.
15a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent */
16a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
17a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#define LOG_TAG "AudioPolicyService"
18a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent//#define LOG_NDEBUG 0
19a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#include <binder/IServiceManager.h>
20a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#include <utils/Log.h>
21a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#include <cutils/properties.h>
22a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#include <binder/IPCThreadState.h>
23a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#include <utils/String16.h>
24a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#include <utils/threads.h>
25a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#include "AudioPolicyService.h"
26a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#include <cutils/properties.h>
27a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#include <dlfcn.h>
28a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
29a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent// ----------------------------------------------------------------------------
30a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent// the sim build doesn't have gettid
31a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
32a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#ifndef HAVE_GETTID
33a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent# define gettid getpid
34a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#endif
35a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
36a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentnamespace android {
37a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
38a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentconst char *AudioPolicyService::sAudioPolicyLibrary = "/system/lib/libaudiopolicy.so";
39a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentconst char *AudioPolicyService::sAudioPolicyGenericLibrary = "/system/lib/libaudiopolicygeneric.so";
40a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
41a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatic bool checkPermission() {
42a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#ifndef HAVE_ANDROID_OS
43a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return true;
44a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#endif
45a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (getpid() == IPCThreadState::self()->getCallingPid()) return true;
46a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    bool ok = checkCallingPermission(String16("android.permission.MODIFY_AUDIO_SETTINGS"));
47a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (!ok) LOGE("Request requires android.permission.MODIFY_AUDIO_SETTINGS");
48a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return ok;
49a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
50a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
51a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent// ----------------------------------------------------------------------------
52a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
53a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric LaurentAudioPolicyService::AudioPolicyService()
54a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    : BnAudioPolicyService() , mpPolicyManager(NULL), mpPolicyManagerLibHandle(NULL)
55a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
56a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    const char *audioPolicyLibrary;
57a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    char value[PROPERTY_VALUE_MAX];
58a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
59a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#if (defined GENERIC_AUDIO) || (defined AUDIO_POLICY_TEST)
60a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    audioPolicyLibrary = sAudioPolicyGenericLibrary;
61a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    LOGV("build for GENERIC_AUDIO - using generic audio policy");
62a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#else
63a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    // if running in emulation - use the emulator driver
64a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (property_get("ro.kernel.qemu", value, 0)) {
65a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        LOGV("Running in emulation - using generic audio policy");
66a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        audioPolicyLibrary = sAudioPolicyGenericLibrary;
67a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
68a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    else {
69a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        LOGV("Using hardware specific audio policy");
70a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        audioPolicyLibrary = sAudioPolicyLibrary;
71a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
72a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent#endif
73a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
74a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
75a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mpPolicyManagerLibHandle = dlopen(audioPolicyLibrary, RTLD_NOW | RTLD_LOCAL);
76a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManagerLibHandle == NULL) {
77a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent       LOGW("Could not load libaudio policy library");
78a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent       return;
79a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
80a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
81a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    AudioPolicyInterface *(*createManager)(AudioPolicyClientInterface *) =
82a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            reinterpret_cast<AudioPolicyInterface* (*)(AudioPolicyClientInterface *)>(dlsym(mpPolicyManagerLibHandle, "createAudioPolicyManager"));
83a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
84a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (createManager == NULL ) {
85a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        LOGW("Could not get createAudioPolicyManager method");
86a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return;
87a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
88a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
89a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    // start tone playback thread
90a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mTonePlaybacThread = new AudioCommandThread();
91a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    // start audio commands thread
92a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mAudioCommandThread = new AudioCommandThread();
93a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
94a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mpPolicyManager = (*createManager)(this);
95a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
96a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    // load properties
97a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    property_get("ro.camera.sound.forced", value, "0");
98a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mpPolicyManager->setSystemProperty("ro.camera.sound.forced", value);
99a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
100a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
101a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric LaurentAudioPolicyService::~AudioPolicyService()
102a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
103a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mTonePlaybacThread->exit();
104a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mTonePlaybacThread.clear();
105a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mAudioCommandThread->exit();
106a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mAudioCommandThread.clear();
107a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
108a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager) {
109a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        void(*destroyManager)(AudioPolicyInterface *) =
110a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                reinterpret_cast<void(*)(AudioPolicyInterface *)>(dlsym(mpPolicyManagerLibHandle, "destroyAudioPolicyManager"));
111a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
112a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        if (destroyManager == NULL ) {
113a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            LOGW("Could not get destroyAudioPolicyManager method");
114a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            return;
115a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        }
116a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        (*destroyManager)(mpPolicyManager);
117a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
118a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
119a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
120a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
121a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::setDeviceConnectionState(AudioSystem::audio_devices device,
122a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                                  AudioSystem::device_connection_state state,
123a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                                  const char *device_address)
124a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
125a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
126a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NO_INIT;
127a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
128a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (!checkPermission()) {
129a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return PERMISSION_DENIED;
130a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
131a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (!AudioSystem::isOutputDevice(device) && !AudioSystem::isInputDevice(device)) {
132a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return BAD_VALUE;
133a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
134a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (state != AudioSystem::DEVICE_STATE_AVAILABLE && state != AudioSystem::DEVICE_STATE_UNAVAILABLE) {
135a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return BAD_VALUE;
136a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
137a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
138a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    LOGV("setDeviceConnectionState() tid %d", gettid());
139a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
140a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return mpPolicyManager->setDeviceConnectionState(device, state, device_address);
141a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
142a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
143a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric LaurentAudioSystem::device_connection_state AudioPolicyService::getDeviceConnectionState(AudioSystem::audio_devices device,
144a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                                  const char *device_address)
145a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
146a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
147a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return AudioSystem::DEVICE_STATE_UNAVAILABLE;
148a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
149a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (!checkPermission()) {
150a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return AudioSystem::DEVICE_STATE_UNAVAILABLE;
151a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
152a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return mpPolicyManager->getDeviceConnectionState(device, device_address);
153a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
154a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
155a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::setPhoneState(int state)
156a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
157a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
158a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NO_INIT;
159a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
160a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (!checkPermission()) {
161a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return PERMISSION_DENIED;
162a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
163a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (state < 0 || state >= AudioSystem::NUM_MODES) {
164a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return BAD_VALUE;
165a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
166a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
167a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    LOGV("setPhoneState() tid %d", gettid());
168a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
169a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    // TODO: check if it is more appropriate to do it in platform specific policy manager
170a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    AudioSystem::setMode(state);
171a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
172a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
173a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mpPolicyManager->setPhoneState(state);
174a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return NO_ERROR;
175a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
176a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
177a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::setRingerMode(uint32_t mode, uint32_t mask)
178a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
179a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
180a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NO_INIT;
181a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
182a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (!checkPermission()) {
183a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return PERMISSION_DENIED;
184a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
185a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
186a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mpPolicyManager->setRingerMode(mode, mask);
187a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return NO_ERROR;
188a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
189a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
190a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::setForceUse(AudioSystem::force_use usage, AudioSystem::forced_config config)
191a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
192a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
193a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NO_INIT;
194a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
195a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (!checkPermission()) {
196a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return PERMISSION_DENIED;
197a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
198a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (usage < 0 || usage >= AudioSystem::NUM_FORCE_USE) {
199a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return BAD_VALUE;
200a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
201a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (config < 0 || config >= AudioSystem::NUM_FORCE_CONFIG) {
202a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return BAD_VALUE;
203a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
204a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    LOGV("setForceUse() tid %d", gettid());
205a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
206a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mpPolicyManager->setForceUse(usage, config);
207a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return NO_ERROR;
208a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
209a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
210a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric LaurentAudioSystem::forced_config AudioPolicyService::getForceUse(AudioSystem::force_use usage)
211a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
212a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
213a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return AudioSystem::FORCE_NONE;
214a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
215a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (!checkPermission()) {
216a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return AudioSystem::FORCE_NONE;
217a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
218a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (usage < 0 || usage >= AudioSystem::NUM_FORCE_USE) {
219a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return AudioSystem::FORCE_NONE;
220a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
221a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return mpPolicyManager->getForceUse(usage);
222a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
223a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
224a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentaudio_io_handle_t AudioPolicyService::getOutput(AudioSystem::stream_type stream,
225a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                    uint32_t samplingRate,
226a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                    uint32_t format,
227a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                    uint32_t channels,
228a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                    AudioSystem::output_flags flags)
229a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
230a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
231a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NULL;
232a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
233a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    LOGV("getOutput() tid %d", gettid());
234a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
235a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return mpPolicyManager->getOutput(stream, samplingRate, format, channels, flags);
236a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
237a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
238a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::startOutput(audio_io_handle_t output, AudioSystem::stream_type stream)
239a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
240a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
241a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NO_INIT;
242a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
243a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    LOGV("startOutput() tid %d", gettid());
244a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
245a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return mpPolicyManager->startOutput(output, stream);
246a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
247a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
248a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::stopOutput(audio_io_handle_t output, AudioSystem::stream_type stream)
249a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
250a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
251a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NO_INIT;
252a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
253a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    LOGV("stopOutput() tid %d", gettid());
254a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
255a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return mpPolicyManager->stopOutput(output, stream);
256a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
257a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
258a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentvoid AudioPolicyService::releaseOutput(audio_io_handle_t output)
259a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
260a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
261a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return;
262a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
263a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    LOGV("releaseOutput() tid %d", gettid());
264a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
265a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mpPolicyManager->releaseOutput(output);
266a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
267a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
268a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentaudio_io_handle_t AudioPolicyService::getInput(int inputSource,
269a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                    uint32_t samplingRate,
270a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                    uint32_t format,
271a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                    uint32_t channels,
272a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                    AudioSystem::audio_in_acoustics acoustics)
273a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
274a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
275a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NULL;
276a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
277a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
278a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return mpPolicyManager->getInput(inputSource, samplingRate, format, channels, acoustics);
279a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
280a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
281a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::startInput(audio_io_handle_t input)
282a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
283a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
284a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NO_INIT;
285a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
286a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
287a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return mpPolicyManager->startInput(input);
288a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
289a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
290a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::stopInput(audio_io_handle_t input)
291a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
292a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
293a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NO_INIT;
294a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
295a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
296a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return mpPolicyManager->stopInput(input);
297a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
298a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
299a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentvoid AudioPolicyService::releaseInput(audio_io_handle_t input)
300a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
301a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
302a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return;
303a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
304a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
305a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mpPolicyManager->releaseInput(input);
306a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
307a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
308a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::initStreamVolume(AudioSystem::stream_type stream,
309a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                            int indexMin,
310a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                            int indexMax)
311a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
312a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
313a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NO_INIT;
314a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
315a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (!checkPermission()) {
316a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return PERMISSION_DENIED;
317a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
318a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (stream < 0 || stream >= AudioSystem::NUM_STREAM_TYPES) {
319a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return BAD_VALUE;
320a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
321a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mpPolicyManager->initStreamVolume(stream, indexMin, indexMax);
322a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return NO_ERROR;
323a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
324a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
325a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::setStreamVolumeIndex(AudioSystem::stream_type stream, int index)
326a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
327a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
328a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NO_INIT;
329a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
330a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (!checkPermission()) {
331a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return PERMISSION_DENIED;
332a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
333a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (stream < 0 || stream >= AudioSystem::NUM_STREAM_TYPES) {
334a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return BAD_VALUE;
335a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
336a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
337a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return mpPolicyManager->setStreamVolumeIndex(stream, index);
338a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
339a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
340a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::getStreamVolumeIndex(AudioSystem::stream_type stream, int *index)
341a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
342a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpPolicyManager == NULL) {
343a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NO_INIT;
344a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
345a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (!checkPermission()) {
346a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return PERMISSION_DENIED;
347a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
348a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (stream < 0 || stream >= AudioSystem::NUM_STREAM_TYPES) {
349a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return BAD_VALUE;
350a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
351a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return mpPolicyManager->getStreamVolumeIndex(stream, index);
352a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
353a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
354a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentvoid AudioPolicyService::binderDied(const wp<IBinder>& who) {
355a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    LOGW("binderDied() %p, tid %d, calling tid %d", who.unsafe_get(), gettid(), IPCThreadState::self()->getCallingPid());
356a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
357a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
358a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::dump(int fd, const Vector<String16>& args)
359a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
360a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (checkCallingPermission(String16("android.permission.DUMP")) == false) {
361a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        dumpPermissionDenial(fd, args);
362a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    } else {
363a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
364a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
365a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return NO_ERROR;
366a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
367a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
368a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::dumpPermissionDenial(int fd, const Vector<String16>& args)
369a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
370a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    const size_t SIZE = 256;
371a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    char buffer[SIZE];
372a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    String8 result;
373a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    snprintf(buffer, SIZE, "Permission Denial: "
374a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            "can't dump AudioPolicyService from pid=%d, uid=%d\n",
375a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            IPCThreadState::self()->getCallingPid(),
376a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            IPCThreadState::self()->getCallingUid());
377a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    result.append(buffer);
378a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    write(fd, result.string(), result.size());
379a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return NO_ERROR;
380a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
381a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
382a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::onTransact(
383a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
384a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
385a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return BnAudioPolicyService::onTransact(code, data, reply, flags);
386a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
387a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
388a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
389a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent// ----------------------------------------------------------------------------
390a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentvoid AudioPolicyService::instantiate() {
391a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    defaultServiceManager()->addService(
392a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            String16("media.audio_policy"), new AudioPolicyService());
393a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
394a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
395a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
396a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent// ----------------------------------------------------------------------------
397a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent// AudioPolicyClientInterface implementation
398a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent// ----------------------------------------------------------------------------
399a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
400a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
401a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentaudio_io_handle_t AudioPolicyService::openOutput(uint32_t *pDevices,
402a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                uint32_t *pSamplingRate,
403a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                uint32_t *pFormat,
404a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                uint32_t *pChannels,
405a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                uint32_t *pLatencyMs,
406a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                AudioSystem::output_flags flags)
407a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
408a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    sp<IAudioFlinger> af = AudioSystem::get_audio_flinger();
409a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (af == 0) {
410a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        LOGW("openOutput() could not get AudioFlinger");
411a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NULL;
412a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
413a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
414a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return af->openOutput(pDevices, pSamplingRate, (uint32_t *)pFormat, pChannels, pLatencyMs, flags);
415a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
416a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
417a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentaudio_io_handle_t AudioPolicyService::openDuplicateOutput(audio_io_handle_t output1, audio_io_handle_t output2)
418a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
419a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    sp<IAudioFlinger> af = AudioSystem::get_audio_flinger();
420a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (af == 0) {
421a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        LOGW("openDuplicateOutput() could not get AudioFlinger");
422a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NULL;
423a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
424a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return af->openDuplicateOutput(output1, output2);
425a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
426a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
427a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::closeOutput(audio_io_handle_t output)
428a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
429a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    sp<IAudioFlinger> af = AudioSystem::get_audio_flinger();
430a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (af == 0) return PERMISSION_DENIED;
431a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
432a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return af->closeOutput(output);
433a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
434a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
435a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
436a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::suspendOutput(audio_io_handle_t output)
437a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
438a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    sp<IAudioFlinger> af = AudioSystem::get_audio_flinger();
439a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (af == 0) {
440a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        LOGW("suspendOutput() could not get AudioFlinger");
441a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return PERMISSION_DENIED;
442a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
443a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
444a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return af->suspendOutput(output);
445a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
446a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
447a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::restoreOutput(audio_io_handle_t output)
448a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
449a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    sp<IAudioFlinger> af = AudioSystem::get_audio_flinger();
450a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (af == 0) {
451a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        LOGW("restoreOutput() could not get AudioFlinger");
452a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return PERMISSION_DENIED;
453a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
454a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
455a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return af->restoreOutput(output);
456a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
457a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
458a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentaudio_io_handle_t AudioPolicyService::openInput(uint32_t *pDevices,
459a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                uint32_t *pSamplingRate,
460a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                uint32_t *pFormat,
461a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                uint32_t *pChannels,
462a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                                uint32_t acoustics)
463a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
464a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    sp<IAudioFlinger> af = AudioSystem::get_audio_flinger();
465a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (af == 0) {
466a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        LOGW("openInput() could not get AudioFlinger");
467a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        return NULL;
468a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
469a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
470a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return af->openInput(pDevices, pSamplingRate, (uint32_t *)pFormat, pChannels, acoustics);
471a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
472a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
473a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::closeInput(audio_io_handle_t input)
474a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
475a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    sp<IAudioFlinger> af = AudioSystem::get_audio_flinger();
476a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (af == 0) return PERMISSION_DENIED;
477a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
478a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return af->closeInput(input);
479a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
480a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
481a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::setStreamVolume(AudioSystem::stream_type stream, float volume, audio_io_handle_t output)
482a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
483a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return mAudioCommandThread->volumeCommand((int)stream, volume, (void *)output);
484a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
485a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
486a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::setStreamOutput(AudioSystem::stream_type stream, audio_io_handle_t output)
487a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
488a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    sp<IAudioFlinger> af = AudioSystem::get_audio_flinger();
489a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (af == 0) return PERMISSION_DENIED;
490a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
491a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return af->setStreamOutput(stream, output);
492a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
493a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
494a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
495a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentvoid AudioPolicyService::setParameters(audio_io_handle_t ioHandle, const String8& keyValuePairs)
496a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
497a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mAudioCommandThread->parametersCommand((void *)ioHandle, keyValuePairs);
498a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
499a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
500a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric LaurentString8 AudioPolicyService::getParameters(audio_io_handle_t ioHandle, const String8& keys)
501a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
502a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    String8 result = AudioSystem::getParameters(ioHandle, keys);
503a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return result;
504a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
505a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
506a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::startTone(ToneGenerator::tone_type tone, AudioSystem::stream_type stream)
507a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
508a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mTonePlaybacThread->startToneCommand(tone, stream);
509a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return NO_ERROR;
510a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
511a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
512a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::stopTone()
513a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
514a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mTonePlaybacThread->stopToneCommand();
515a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return NO_ERROR;
516a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
517a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
518a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
519a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent// -----------  AudioPolicyService::AudioCommandThread implementation ----------
520a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
521a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric LaurentAudioPolicyService::AudioCommandThread::AudioCommandThread()
522a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    :   Thread(false)
523a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
524a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mpToneGenerator = NULL;
525a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
526a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
527a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
528a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric LaurentAudioPolicyService::AudioCommandThread::~AudioCommandThread()
529a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
530a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mAudioCommands.clear();
531a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    if (mpToneGenerator != NULL) delete mpToneGenerator;
532a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
533a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
534a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentvoid AudioPolicyService::AudioCommandThread::onFirstRef()
535a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
536a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    const size_t SIZE = 256;
537a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    char buffer[SIZE];
538a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
539a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    snprintf(buffer, SIZE, "AudioCommandThread");
540a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
541a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    run(buffer, ANDROID_PRIORITY_AUDIO);
542a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
543a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
544a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentbool AudioPolicyService::AudioCommandThread::threadLoop()
545a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
546a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mLock.lock();
547a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    while (!exitPending())
548a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    {
549a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        while(!mAudioCommands.isEmpty()) {
550a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            AudioCommand *command = mAudioCommands[0];
551a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            mAudioCommands.removeAt(0);
552a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            switch (command->mCommand) {
553a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            case START_TONE: {
554a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                mLock.unlock();
555a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                ToneData *data = (ToneData *)command->mParam;
556a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                LOGV("AudioCommandThread() processing start tone %d on stream %d",
557a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                        data->mType, data->mStream);
558a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                if (mpToneGenerator != NULL)
559a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                    delete mpToneGenerator;
560a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                mpToneGenerator = new ToneGenerator(data->mStream, 1.0);
561a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                mpToneGenerator->startTone(data->mType);
562a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                delete data;
563a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                mLock.lock();
564a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                }break;
565a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            case STOP_TONE: {
566a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                mLock.unlock();
567a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                LOGV("AudioCommandThread() processing stop tone");
568a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                if (mpToneGenerator != NULL) {
569a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                    mpToneGenerator->stopTone();
570a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                    delete mpToneGenerator;
571a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                    mpToneGenerator = NULL;
572a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                }
573a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                mLock.lock();
574a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                }break;
575a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            case SET_VOLUME: {
576a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                VolumeData *data = (VolumeData *)command->mParam;
577a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                LOGV("AudioCommandThread() processing set volume stream %d, volume %f, output %p", data->mStream, data->mVolume, data->mIO);
578a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                mCommandStatus = AudioSystem::setStreamVolume(data->mStream, data->mVolume, data->mIO);
579a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                mCommandCond.signal();
580a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                mWaitWorkCV.wait(mLock);
581a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                delete data;
582a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                }break;
583a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            case SET_PARAMETERS: {
584a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                 ParametersData *data = (ParametersData *)command->mParam;
585a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                 LOGV("AudioCommandThread() processing set parameters string %s, io %p", data->mKeyValuePairs.string(), data->mIO);
586a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                 mCommandStatus = AudioSystem::setParameters(data->mIO, data->mKeyValuePairs);
587a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                 mCommandCond.signal();
588a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                 mWaitWorkCV.wait(mLock);
589a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                 delete data;
590a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                 }break;
591a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            default:
592a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent                LOGW("AudioCommandThread() unknown command %d", command->mCommand);
593a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            }
594a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent            delete command;
595a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        }
596a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        LOGV("AudioCommandThread() going to sleep");
597a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        mWaitWorkCV.wait(mLock);
598a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        LOGV("AudioCommandThread() waking up");
599a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
600a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mLock.unlock();
601a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return false;
602a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
603a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
604a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentvoid AudioPolicyService::AudioCommandThread::startToneCommand(int type, int stream)
605a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
606a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
607a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    AudioCommand *command = new AudioCommand();
608a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    command->mCommand = START_TONE;
609a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    ToneData *data = new ToneData();
610a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    data->mType = type;
611a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    data->mStream = stream;
612a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    command->mParam = (void *)data;
613a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mAudioCommands.add(command);
614a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    LOGV("AudioCommandThread() adding tone start type %d, stream %d", type, stream);
615a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mWaitWorkCV.signal();
616a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
617a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
618a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentvoid AudioPolicyService::AudioCommandThread::stopToneCommand()
619a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
620a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
621a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    AudioCommand *command = new AudioCommand();
622a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    command->mCommand = STOP_TONE;
623a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    command->mParam = NULL;
624a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mAudioCommands.add(command);
625a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    LOGV("AudioCommandThread() adding tone stop");
626a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mWaitWorkCV.signal();
627a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
628a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
629a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::AudioCommandThread::volumeCommand(int stream, float volume, void *output)
630a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
631a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
632a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    AudioCommand *command = new AudioCommand();
633a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    command->mCommand = SET_VOLUME;
634a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    VolumeData *data = new VolumeData();
635a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    data->mStream = stream;
636a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    data->mVolume = volume;
637a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    data->mIO = output;
638a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    command->mParam = data;
639a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mAudioCommands.add(command);
640a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    LOGV("AudioCommandThread() adding set volume stream %d, volume %f, output %p", stream, volume, output);
641a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mWaitWorkCV.signal();
642a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mCommandCond.wait(mLock);
643a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    status_t status =  mCommandStatus;
644a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mWaitWorkCV.signal();
645a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return status;
646a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
647a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
648a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentstatus_t AudioPolicyService::AudioCommandThread::parametersCommand(void *ioHandle, const String8& keyValuePairs)
649a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
650a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    Mutex::Autolock _l(mLock);
651a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    AudioCommand *command = new AudioCommand();
652a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    command->mCommand = SET_PARAMETERS;
653a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    ParametersData *data = new ParametersData();
654a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    data->mIO = ioHandle;
655a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    data->mKeyValuePairs = keyValuePairs;
656a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    command->mParam = data;
657a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mAudioCommands.add(command);
658a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    LOGV("AudioCommandThread() adding set parameter string %s, io %p", keyValuePairs.string(), ioHandle);
659a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mWaitWorkCV.signal();
660a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mCommandCond.wait(mLock);
661a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    status_t status =  mCommandStatus;
662a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    mWaitWorkCV.signal();
663a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    return status;
664a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
665a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
666a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurentvoid AudioPolicyService::AudioCommandThread::exit()
667a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent{
668a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    LOGV("AudioCommandThread::exit");
669a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    {
670a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        AutoMutex _l(mLock);
671a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        requestExit();
672a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent        mWaitWorkCV.signal();
673a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    }
674a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent    requestExitAndWait();
675a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}
676a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent
677a553c25b33c99b345cf1c8688f8df0ed8df14e5aEric Laurent}; // namespace android
678