blob: 6bc3d1e22c472c8ec7dd6d064e7285a673c2d5bb [file] [log] [blame]
Marko Manef8d7e42018-08-26 23:20:31 +02001/*
2 * Copyright (c) 2013-2018 The Linux Foundation. All rights reserved.
3 * Not a contribution.
4 *
5 * Copyright (C) 2009 The Android Open Source Project
6 *
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
10 *
11 * http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
18 */
19
20#define LOG_TAG "AudioPolicyManagerCustom"
21//#define LOG_NDEBUG 0
22
23//#define VERY_VERBOSE_LOGGING
24#ifdef VERY_VERBOSE_LOGGING
25#define ALOGVV ALOGV
26#else
27#define ALOGVV(a...) do { } while(0)
28#endif
29
30// A device mask for all audio output devices that are considered "remote" when evaluating
31// active output devices in isStreamActiveRemotely()
32#define APM_AUDIO_OUT_DEVICE_REMOTE_ALL AUDIO_DEVICE_OUT_REMOTE_SUBMIX
33// A device mask for all audio input and output devices where matching inputs/outputs on device
34// type alone is not enough: the address must match too
35#define APM_AUDIO_DEVICE_MATCH_ADDRESS_ALL (AUDIO_DEVICE_IN_REMOTE_SUBMIX | \
36 AUDIO_DEVICE_OUT_REMOTE_SUBMIX)
37#define SAMPLE_RATE_8000 8000
38#include <inttypes.h>
39#include <math.h>
40
41#include <cutils/properties.h>
42#include <utils/Log.h>
43#include <hardware/audio.h>
44#include <hardware/audio_effect.h>
45#include <media/AudioParameter.h>
46#include <soundtrigger/SoundTrigger.h>
47#include "AudioPolicyManager.h"
48#include <policy.h>
49
50namespace android {
51/*audio policy: workaround for truncated touch sounds*/
52//FIXME: workaround for truncated touch sounds
53// to be removed when the problem is handled by system UI
54#define TOUCH_SOUND_FIXED_DELAY_MS 100
55#ifdef VOICE_CONCURRENCY
56audio_output_flags_t AudioPolicyManagerCustom::getFallBackPath()
57{
58 audio_output_flags_t flag = AUDIO_OUTPUT_FLAG_FAST;
59 char propValue[PROPERTY_VALUE_MAX];
60
61 if (property_get("vendor.voice.conc.fallbackpath", propValue, NULL)) {
62 if (!strncmp(propValue, "deep-buffer", 11)) {
63 flag = AUDIO_OUTPUT_FLAG_DEEP_BUFFER;
64 }
65 else if (!strncmp(propValue, "fast", 4)) {
66 flag = AUDIO_OUTPUT_FLAG_FAST;
67 }
68 else {
69 ALOGD("voice_conc:not a recognised path(%s) in prop vendor.voice.conc.fallbackpath",
70 propValue);
71 }
72 }
73 else {
74 ALOGD("voice_conc:prop vendor.voice.conc.fallbackpath not set");
75 }
76
77 ALOGD("voice_conc:picked up flag(0x%x) from prop vendor.voice.conc.fallbackpath",
78 flag);
79
80 return flag;
81}
82#endif /*VOICE_CONCURRENCY*/
83
84void AudioPolicyManagerCustom::moveGlobalEffect()
85{
86 audio_io_handle_t dstOutput = getOutputForEffect();
87 if (hasPrimaryOutput() && dstOutput != mPrimaryOutput->mIoHandle)
88 mpClientInterface->moveEffects(AUDIO_SESSION_OUTPUT_MIX,
89 mPrimaryOutput->mIoHandle, dstOutput);
90}
91
92// ----------------------------------------------------------------------------
93// AudioPolicyInterface implementation
94// ----------------------------------------------------------------------------
95extern "C" AudioPolicyInterface* createAudioPolicyManager(
96 AudioPolicyClientInterface *clientInterface)
97{
98 return new AudioPolicyManagerCustom(clientInterface);
99}
100
101extern "C" void destroyAudioPolicyManager(AudioPolicyInterface *interface)
102{
103 delete interface;
104}
105
106status_t AudioPolicyManagerCustom::setDeviceConnectionStateInt(audio_devices_t device,
107 audio_policy_dev_state_t state,
108 const char *device_address,
109 const char *device_name)
110{
111 ALOGD("setDeviceConnectionStateInt() device: 0x%X, state %d, address %s name %s",
112 device, state, device_address, device_name);
113
114 // connect/disconnect only 1 device at a time
115 if (!audio_is_output_device(device) && !audio_is_input_device(device)) return BAD_VALUE;
116
117 sp<DeviceDescriptor> devDesc =
118 mHwModules.getDeviceDescriptor(device, device_address, device_name);
119
120 // handle output devices
121 if (audio_is_output_device(device)) {
122 SortedVector <audio_io_handle_t> outputs;
123
124 ssize_t index = mAvailableOutputDevices.indexOf(devDesc);
125
126 // save a copy of the opened output descriptors before any output is opened or closed
127 // by checkOutputsForDevice(). This will be needed by checkOutputForAllStrategies()
128 mPreviousOutputs = mOutputs;
129 switch (state)
130 {
131 // handle output device connection
132 case AUDIO_POLICY_DEVICE_STATE_AVAILABLE: {
133 if (index >= 0) {
134#ifdef AUDIO_EXTN_HDMI_SPK_ENABLED
135 if ((popcount(device) == 1) && (device & AUDIO_DEVICE_OUT_AUX_DIGITAL)) {
136 if (!strncmp(device_address, "hdmi_spkr", 9)) {
137 mHdmiAudioDisabled = false;
138 } else {
139 mHdmiAudioEvent = true;
140 }
141 }
142#endif
143 ALOGW("setDeviceConnectionState() device already connected: %x", device);
144 return INVALID_OPERATION;
145 }
146 ALOGV("setDeviceConnectionState() connecting device %x", device);
147
148 // register new device as available
149 index = mAvailableOutputDevices.add(devDesc);
150#ifdef AUDIO_EXTN_HDMI_SPK_ENABLED
151 if ((popcount(device) == 1) && (device & AUDIO_DEVICE_OUT_AUX_DIGITAL)) {
152 if (!strncmp(device_address, "hdmi_spkr", 9)) {
153 mHdmiAudioDisabled = false;
154 } else {
155 mHdmiAudioEvent = true;
156 }
157 if (mHdmiAudioDisabled || !mHdmiAudioEvent) {
158 mAvailableOutputDevices.remove(devDesc);
159 ALOGW("HDMI sink not connected, do not route audio to HDMI out");
160 return INVALID_OPERATION;
161 }
162 }
163#endif
164 if (index >= 0) {
165 sp<HwModule> module = mHwModules.getModuleForDevice(device);
166 if (module == 0) {
167 ALOGD("setDeviceConnectionState() could not find HW module for device %08x",
168 device);
169 mAvailableOutputDevices.remove(devDesc);
170 return INVALID_OPERATION;
171 }
172 mAvailableOutputDevices[index]->attach(module);
173 } else {
174 return NO_MEMORY;
175 }
176
177 // Before checking outputs, broadcast connect event to allow HAL to retrieve dynamic
178 // parameters on newly connected devices (instead of opening the outputs...)
179 broadcastDeviceConnectionState(device, state, devDesc->mAddress);
180
181 if (checkOutputsForDevice(devDesc, state, outputs, devDesc->mAddress) != NO_ERROR) {
182 mAvailableOutputDevices.remove(devDesc);
183
184 broadcastDeviceConnectionState(device, AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
185 devDesc->mAddress);
186 return INVALID_OPERATION;
187 }
188 // Propagate device availability to Engine
189 mEngine->setDeviceConnectionState(devDesc, state);
190 if (device == AUDIO_DEVICE_OUT_AUX_DIGITAL) {
191 chkDpConnAndAllowedForVoice();
192 }
193
194 // outputs should never be empty here
195 ALOG_ASSERT(outputs.size() != 0, "setDeviceConnectionState():"
196 "checkOutputsForDevice() returned no outputs but status OK");
197 ALOGV("setDeviceConnectionState() checkOutputsForDevice() returned %zu outputs",
198 outputs.size());
199
200 } break;
201 // handle output device disconnection
202 case AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE: {
203 if (index < 0) {
204#ifdef AUDIO_EXTN_HDMI_SPK_ENABLED
205 if ((popcount(device) == 1) && (device & AUDIO_DEVICE_OUT_AUX_DIGITAL)) {
206 if (!strncmp(device_address, "hdmi_spkr", 9)) {
207 mHdmiAudioDisabled = true;
208 } else {
209 mHdmiAudioEvent = false;
210 }
211 }
212#endif
213 ALOGW("setDeviceConnectionState() device not connected: %x", device);
214 return INVALID_OPERATION;
215 }
216
217 ALOGV("setDeviceConnectionState() disconnecting output device %x", device);
218
219 // Send Disconnect to HALs
220 broadcastDeviceConnectionState(device, state, devDesc->mAddress);
221
222 // remove device from available output devices
223 mAvailableOutputDevices.remove(devDesc);
224#ifdef AUDIO_EXTN_HDMI_SPK_ENABLED
225 if ((popcount(device) == 1) && (device & AUDIO_DEVICE_OUT_AUX_DIGITAL)) {
226 if (!strncmp(device_address, "hdmi_spkr", 9)) {
227 mHdmiAudioDisabled = true;
228 } else {
229 mHdmiAudioEvent = false;
230 }
231 }
232#endif
233 checkOutputsForDevice(devDesc, state, outputs, devDesc->mAddress);
234
235 // Propagate device availability to Engine
236 mEngine->setDeviceConnectionState(devDesc, state);
237 if (device == AUDIO_DEVICE_OUT_AUX_DIGITAL) {
238 mEngine->setDpConnAndAllowedForVoice(false);
239 }
240 } break;
241
242 default:
243 ALOGE("setDeviceConnectionState() invalid state: %x", state);
244 return BAD_VALUE;
245 }
246
247 // checkA2dpSuspend must run before checkOutputForAllStrategies so that A2DP
248 // output is suspended before any tracks are moved to it
249 checkA2dpSuspend();
250
251 if (!outputs.isEmpty()) {
252 for (size_t i = 0; i < outputs.size(); i++) {
253 sp<SwAudioOutputDescriptor> desc = mOutputs.valueFor(outputs[i]);
254 // close voip output before track invalidation to allow creation of
255 // new voip stream from restoreTrack
256 if((desc->mFlags == (AUDIO_OUTPUT_FLAG_DIRECT | AUDIO_OUTPUT_FLAG_VOIP_RX)) != 0) {
257 closeOutput(outputs[i]);
258 outputs.remove(outputs[i]);
259 }
260 }
261 }
262
263 checkOutputForAllStrategies();
264 // outputs must be closed after checkOutputForAllStrategies() is executed
265 if (!outputs.isEmpty()) {
266 for (size_t i = 0; i < outputs.size(); i++) {
267 sp<SwAudioOutputDescriptor> desc = mOutputs.valueFor(outputs[i]);
268 // close unused outputs after device disconnection or direct outputs that have been
269 // opened by checkOutputsForDevice() to query dynamic parameters
270 if ((state == AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE) ||
271 (((desc->mFlags & AUDIO_OUTPUT_FLAG_DIRECT) != 0) &&
272 (desc->mDirectOpenCount == 0))) {
273 closeOutput(outputs[i]);
274 }
275 }
276 // check again after closing A2DP output to reset mA2dpSuspended if needed
277 checkA2dpSuspend();
278 }
279
280#ifdef FM_POWER_OPT
281 // handle FM device connection state to trigger FM AFE loopback
282 if (device == AUDIO_DEVICE_OUT_FM && hasPrimaryOutput()) {
283 audio_devices_t newDevice = AUDIO_DEVICE_NONE;
284 if (state == AUDIO_POLICY_DEVICE_STATE_AVAILABLE) {
285 /*
286 when mPrimaryOutput->start() is called for FM it would check if isActive() is true
287 or not as mRefCount=0 so isActive() would return false and curActiveCount will be
288 1 and then the mRefCount will be increased by 1 for FM case.Updating curActiveCount
289 is important as in case of adding other tracks when FM is still active isActive()
290 will always be true as mRefCount will always be > 0,Hence curActiveCount will never
291 update for them. However ,when fm stops and the track stops too mRefCount will be 0
292 isActive will false,it will check if curActiveCount < 1 as curActiveCount was never
293 updated so LOG_FATAL will cause the AudioServer to die.Hence this start() call will
294 ensure that curActiveCount is updated at least once when FM starts prior to other
295 tracks and on calling of stop() LOG_FATAL is not called.
296 */
297 mPrimaryOutput->start();
298 mPrimaryOutput->changeRefCount(AUDIO_STREAM_MUSIC, 1);
299 newDevice = (audio_devices_t)(getNewOutputDevice(mPrimaryOutput, false)|AUDIO_DEVICE_OUT_FM);
300 mFMIsActive = true;
301 mPrimaryOutput->mDevice = newDevice & ~AUDIO_DEVICE_OUT_FM;
302 } else {
303 newDevice = (audio_devices_t)(getNewOutputDevice(mPrimaryOutput, false));
304 mFMIsActive = false;
305 mPrimaryOutput->changeRefCount(AUDIO_STREAM_MUSIC, -1);
306 /*
307 mPrimaryOutput->stop() is called as because of calling of start()
308 in FM case curActiveCount is getting updated and hence stop() is
309 called so that curActiveCount gets decremented and if any tracks
310 are added after FM stops they may get curActiveCount=0 ,ouptput
311 curActiveCount can be properly updated
312 */
313 mPrimaryOutput->stop();
314 }
315 AudioParameter param = AudioParameter();
316 param.addInt(String8("handle_fm"), (int)newDevice);
317 mpClientInterface->setParameters(mPrimaryOutput->mIoHandle, param.toString());
318 }
319#endif /* FM_POWER_OPT end */
320
321 updateDevicesAndOutputs();
322 if (mEngine->getPhoneState() == AUDIO_MODE_IN_CALL && hasPrimaryOutput()) {
323 audio_devices_t newDevice = getNewOutputDevice(mPrimaryOutput, false /*fromCache*/);
324 updateCallRouting(newDevice);
325 }
326
327 for (size_t i = 0; i < mOutputs.size(); i++) {
328 sp<SwAudioOutputDescriptor> desc = mOutputs.valueAt(i);
329 if ((mEngine->getPhoneState() != AUDIO_MODE_IN_CALL) || (desc != mPrimaryOutput)) {
330 audio_devices_t newDevice = getNewOutputDevice(desc, true /*fromCache*/);
331 // do not force device change on duplicated output because if device is 0, it will
332 // also force a device 0 for the two outputs it is duplicated to which may override
333 // a valid device selection on those outputs.
334 bool force = !desc->isDuplicated()
335 && (!device_distinguishes_on_address(device)
336 // always force when disconnecting (a non-duplicated device)
337 || (state == AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE));
338 setOutputDevice(desc, newDevice, force, 0);
339 }
340 }
341
342 if (state == AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE) {
343 cleanUpForDevice(devDesc);
344 }
345
346 mpClientInterface->onAudioPortListUpdate();
347 return NO_ERROR;
348 } // end if is output device
349
350 // handle input devices
351 if (audio_is_input_device(device)) {
352 SortedVector <audio_io_handle_t> inputs;
353
354 ssize_t index = mAvailableInputDevices.indexOf(devDesc);
355 switch (state)
356 {
357 // handle input device connection
358 case AUDIO_POLICY_DEVICE_STATE_AVAILABLE: {
359 if (index >= 0) {
360 ALOGW("setDeviceConnectionState() device already connected: %d", device);
361 return INVALID_OPERATION;
362 }
363 sp<HwModule> module = mHwModules.getModuleForDevice(device);
364 if (module == NULL) {
365 ALOGW("setDeviceConnectionState(): could not find HW module for device %08x",
366 device);
367 return INVALID_OPERATION;
368 }
369
370 // Before checking intputs, broadcast connect event to allow HAL to retrieve dynamic
371 // parameters on newly connected devices (instead of opening the inputs...)
372 broadcastDeviceConnectionState(device, state, devDesc->mAddress);
373
374 if (checkInputsForDevice(devDesc, state, inputs, devDesc->mAddress) != NO_ERROR) {
375 broadcastDeviceConnectionState(device, AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
376 devDesc->mAddress);
377 return INVALID_OPERATION;
378 }
379
380 index = mAvailableInputDevices.add(devDesc);
381 if (index >= 0) {
382 mAvailableInputDevices[index]->attach(module);
383 } else {
384 return NO_MEMORY;
385 }
386
387 // Propagate device availability to Engine
388 mEngine->setDeviceConnectionState(devDesc, state);
389 } break;
390
391 // handle input device disconnection
392 case AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE: {
393 if (index < 0) {
394 ALOGW("setDeviceConnectionState() device not connected: %d", device);
395 return INVALID_OPERATION;
396 }
397
398 ALOGV("setDeviceConnectionState() disconnecting input device %x", device);
399
400 // Set Disconnect to HALs
401 broadcastDeviceConnectionState(device, state, devDesc->mAddress);
402
403 checkInputsForDevice(devDesc, state, inputs, devDesc->mAddress);
404 mAvailableInputDevices.remove(devDesc);
405
406 // Propagate device availability to Engine
407 mEngine->setDeviceConnectionState(devDesc, state);
408 } break;
409
410 default:
411 ALOGE("setDeviceConnectionState() invalid state: %x", state);
412 return BAD_VALUE;
413 }
414
415 closeAllInputs();
416 /*audio policy: fix call volume over USB*/
417 // As the input device list can impact the output device selection, update
418 // getDeviceForStrategy() cache
419 updateDevicesAndOutputs();
420
421 if (mEngine->getPhoneState() == AUDIO_MODE_IN_CALL && hasPrimaryOutput()) {
422 audio_devices_t newDevice = getNewOutputDevice(mPrimaryOutput, false /*fromCache*/);
423 updateCallRouting(newDevice);
424 }
425
426 if (state == AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE) {
427 cleanUpForDevice(devDesc);
428 }
429
430 mpClientInterface->onAudioPortListUpdate();
431 return NO_ERROR;
432 } // end if is input device
433
434 ALOGW("setDeviceConnectionState() invalid device: %x", device);
435 return BAD_VALUE;
436}
437
438void AudioPolicyManagerCustom::chkDpConnAndAllowedForVoice()
439{
440 String8 value;
441 bool connAndAllowed = false;
442 String8 valueStr = mpClientInterface->getParameters((audio_io_handle_t)0,
443 String8("dp_for_voice"));
444
445 AudioParameter result = AudioParameter(valueStr);
446 if (result.get(String8("dp_for_voice"), value) == NO_ERROR) {
447 connAndAllowed = value.contains("true");
448 }
449 mEngine->setDpConnAndAllowedForVoice(connAndAllowed);
450}
451
452bool AudioPolicyManagerCustom::isInvalidationOfMusicStreamNeeded(routing_strategy strategy)
453{
454 if (strategy == STRATEGY_MEDIA) {
455 for (size_t i = 0; i < mOutputs.size(); i++) {
456 sp<SwAudioOutputDescriptor> newOutputDesc = mOutputs.valueAt(i);
457 if (newOutputDesc->mFormat == AUDIO_FORMAT_DSD)
458 return false;
459 }
460 }
461 return true;
462}
463
464void AudioPolicyManagerCustom::checkOutputForStrategy(routing_strategy strategy)
465{
466 audio_devices_t oldDevice = getDeviceForStrategy(strategy, true /*fromCache*/);
467 audio_devices_t newDevice = getDeviceForStrategy(strategy, false /*fromCache*/);
468 SortedVector<audio_io_handle_t> srcOutputs = getOutputsForDevice(oldDevice, mOutputs);
469 SortedVector<audio_io_handle_t> dstOutputs = getOutputsForDevice(newDevice, mOutputs);
470
471 // also take into account external policy-related changes: add all outputs which are
472 // associated with policies in the "before" and "after" output vectors
473 ALOGV("checkOutputForStrategy(): policy related outputs");
474 for (size_t i = 0 ; i < mPreviousOutputs.size() ; i++) {
475 const sp<SwAudioOutputDescriptor> desc = mPreviousOutputs.valueAt(i);
476 if (desc != 0 && desc->mPolicyMix != NULL) {
477 srcOutputs.add(desc->mIoHandle);
478 ALOGV(" previous outputs: adding %d", desc->mIoHandle);
479 }
480 }
481 for (size_t i = 0 ; i < mOutputs.size() ; i++) {
482 const sp<SwAudioOutputDescriptor> desc = mOutputs.valueAt(i);
483 if (desc != 0 && desc->mPolicyMix != NULL) {
484 dstOutputs.add(desc->mIoHandle);
485 ALOGV(" new outputs: adding %d", desc->mIoHandle);
486 }
487 }
488
489 if (!vectorsEqual(srcOutputs,dstOutputs) && isInvalidationOfMusicStreamNeeded(strategy)) {
490 AudioPolicyManager::checkOutputForStrategy(strategy);
491 }
492}
493
494// This function checks for the parameters which can be offloaded.
495// This can be enhanced depending on the capability of the DSP and policy
496// of the system.
497bool AudioPolicyManagerCustom::isOffloadSupported(const audio_offload_info_t& offloadInfo)
498{
499 ALOGV("isOffloadSupported: SR=%u, CM=0x%x, Format=0x%x, StreamType=%d,"
500 " BitRate=%u, duration=%" PRId64 " us, has_video=%d",
501 offloadInfo.sample_rate, offloadInfo.channel_mask,
502 offloadInfo.format,
503 offloadInfo.stream_type, offloadInfo.bit_rate, offloadInfo.duration_us,
504 offloadInfo.has_video);
505
506 if (mMasterMono) {
507 return false; // no offloading if mono is set.
508 }
509
510#ifdef VOICE_CONCURRENCY
511 char concpropValue[PROPERTY_VALUE_MAX];
512 if (property_get("vendor.voice.playback.conc.disabled", concpropValue, NULL)) {
513 bool propenabled = atoi(concpropValue) || !strncmp("true", concpropValue, 4);
514 if (propenabled) {
515 if (isInCall())
516 {
517 ALOGD("\n copl: blocking compress offload on call mode\n");
518 return false;
519 }
520 }
521 }
522#endif
523 if (property_get_bool("vendor.voice.dsd.playback.conc.disabled", true) &&
524 isInCall() && (offloadInfo.format == AUDIO_FORMAT_DSD)) {
525 ALOGD("blocking DSD compress offload on call mode");
526 return false;
527 }
528#ifdef RECORD_PLAY_CONCURRENCY
529 char recConcPropValue[PROPERTY_VALUE_MAX];
530 bool prop_rec_play_enabled = false;
531
532 if (property_get("vendor.audio.rec.playback.conc.disabled", recConcPropValue, NULL)) {
533 prop_rec_play_enabled = atoi(recConcPropValue) || !strncmp("true", recConcPropValue, 4);
534 }
535
536 if ((prop_rec_play_enabled) &&
537 ((true == mIsInputRequestOnProgress) || (mInputs.activeInputsCountOnDevices() > 0))) {
538 ALOGD("copl: blocking compress offload for record concurrency");
539 return false;
540 }
541#endif
542 // Check if stream type is music, then only allow offload as of now.
543 if (offloadInfo.stream_type != AUDIO_STREAM_MUSIC)
544 {
545 ALOGV("isOffloadSupported: stream_type != MUSIC, returning false");
546 return false;
547 }
548
549 // Check if offload has been disabled
550 bool offloadDisabled = property_get_bool("audio.offload.disable", false);
551 if (offloadDisabled) {
552 ALOGI("offload disabled by audio.offload.disable=%d", offloadDisabled);
553 return false;
554 }
555
556 //check if it's multi-channel AAC (includes sub formats) and FLAC format
557 if ((popcount(offloadInfo.channel_mask) > 2) &&
558 (((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_AAC) ||
559 ((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_VORBIS))) {
560 ALOGD("offload disabled for multi-channel AAC,FLAC and VORBIS format");
561 return false;
562 }
563
564#ifdef AUDIO_EXTN_FORMATS_ENABLED
565 //check if it's multi-channel FLAC/ALAC/WMA format with sample rate > 48k
566 if ((popcount(offloadInfo.channel_mask) > 2) &&
567 (((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_FLAC) ||
568 (((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_ALAC) && (offloadInfo.sample_rate > 48000)) ||
569 (((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_WMA) && (offloadInfo.sample_rate > 48000)) ||
570 (((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_WMA_PRO) && (offloadInfo.sample_rate > 48000)) ||
571 ((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_AAC_ADTS))) {
572 ALOGD("offload disabled for multi-channel FLAC/ALAC/WMA/AAC_ADTS clips with sample rate > 48kHz");
573 return false;
574 }
575
576 // check against wma std bit rate restriction
577 if ((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_WMA) {
578 int32_t sr_id = -1;
579 uint32_t min_bitrate, max_bitrate;
580 for (int i = 0; i < WMA_STD_NUM_FREQ; i++) {
581 if (offloadInfo.sample_rate == wmaStdSampleRateTbl[i]) {
582 sr_id = i;
583 break;
584 }
585 }
586 if ((sr_id < 0) || (popcount(offloadInfo.channel_mask) > 2)
587 || (popcount(offloadInfo.channel_mask) <= 0)) {
588 ALOGE("invalid sample rate or channel count");
589 return false;
590 }
591
592 min_bitrate = wmaStdMinAvgByteRateTbl[sr_id][popcount(offloadInfo.channel_mask) - 1];
593 max_bitrate = wmaStdMaxAvgByteRateTbl[sr_id][popcount(offloadInfo.channel_mask) - 1];
594 if ((offloadInfo.bit_rate > max_bitrate) || (offloadInfo.bit_rate < min_bitrate)) {
595 ALOGD("offload disabled for WMA clips with unsupported bit rate");
596 ALOGD("bit_rate %d, max_bitrate %d, min_bitrate %d", offloadInfo.bit_rate, max_bitrate, min_bitrate);
597 return false;
598 }
599 }
600
601 // Safely choose the min bitrate as threshold and leave the restriction to NT decoder as we can't distinguish wma pro and wma lossless here.
602 if ((((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_WMA_PRO) && (offloadInfo.bit_rate > MAX_BITRATE_WMA_PRO)) ||
603 (((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_WMA_PRO) && (offloadInfo.bit_rate > MAX_BITRATE_WMA_LOSSLESS))) {
604 ALOGD("offload disabled for WMA_PRO/WMA_LOSSLESS clips with bit rate over maximum supported value");
605 return false;
606 }
607#endif
608 //TODO: enable audio offloading with video when ready
609 const bool allowOffloadWithVideo =
610 property_get_bool("audio.offload.video", false /* default_value */);
611 if (offloadInfo.has_video && !allowOffloadWithVideo) {
612 ALOGV("isOffloadSupported: has_video == true, returning false");
613 return false;
614 }
615
616 const bool allowOffloadStreamingWithVideo =
617 property_get_bool("vendor.audio.av.streaming.offload.enable", false /*default value*/);
618 if (offloadInfo.has_video && offloadInfo.is_streaming && !allowOffloadStreamingWithVideo) {
619 ALOGW("offload disabled by vendor.audio.av.streaming.offload.enable %d",
620 allowOffloadStreamingWithVideo);
621 return false;
622 }
623
624 //If duration is less than minimum value defined in property, return false
625 char propValue[PROPERTY_VALUE_MAX];
626 if (property_get("audio.offload.min.duration.secs", propValue, NULL)) {
627 if (offloadInfo.duration_us < (atoi(propValue) * 1000000 )) {
628 ALOGV("Offload denied by duration < audio.offload.min.duration.secs(=%s)", propValue);
629 return false;
630 }
631 } else if (offloadInfo.duration_us < OFFLOAD_DEFAULT_MIN_DURATION_SECS * 1000000) {
632 ALOGV("Offload denied by duration < default min(=%u)", OFFLOAD_DEFAULT_MIN_DURATION_SECS);
633 //duration checks only valid for MP3/AAC/ formats,
634 //do not check duration for other audio formats, e.g. AAC/AC3 and amrwb+ formats
635 if ((offloadInfo.format == AUDIO_FORMAT_MP3) ||
636 ((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_AAC) ||
637 ((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_FLAC) ||
638 ((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_VORBIS))
639 return false;
640
641#ifdef AUDIO_EXTN_FORMATS_ENABLED
642 if (((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_WMA) ||
643 ((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_WMA_PRO) ||
644 ((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_ALAC) ||
645 ((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_APE) ||
646 ((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_DSD) ||
647 ((offloadInfo.format & AUDIO_FORMAT_MAIN_MASK) == AUDIO_FORMAT_AAC_ADTS))
648 return false;
649#endif
650 }
651
652 // Do not allow offloading if one non offloadable effect is enabled. This prevents from
653 // creating an offloaded track and tearing it down immediately after start when audioflinger
654 // detects there is an active non offloadable effect.
655 // FIXME: We should check the audio session here but we do not have it in this context.
656 // This may prevent offloading in rare situations where effects are left active by apps
657 // in the background.
658 if (mEffects.isNonOffloadableEffectEnabled()) {
659 return false;
660 }
661
662 // See if there is a profile to support this.
663 // AUDIO_DEVICE_NONE
664 sp<IOProfile> profile = getProfileForDirectOutput(AUDIO_DEVICE_NONE /*ignore device */,
665 offloadInfo.sample_rate,
666 offloadInfo.format,
667 offloadInfo.channel_mask,
668 AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD);
669 ALOGV("isOffloadSupported() profile %sfound", profile != 0 ? "" : "NOT ");
670 return (profile != 0);
671}
672
673void AudioPolicyManagerCustom::setPhoneState(audio_mode_t state)
674{
675 ALOGD("setPhoneState() state %d", state);
676 // store previous phone state for management of sonification strategy below
677 audio_devices_t newDevice = AUDIO_DEVICE_NONE;
678 int oldState = mEngine->getPhoneState();
679
680 if (mEngine->setPhoneState(state) != NO_ERROR) {
681 ALOGW("setPhoneState() invalid or same state %d", state);
682 return;
683 }
684 /// Opens: can these line be executed after the switch of volume curves???
685 // if leaving call state, handle special case of active streams
686 // pertaining to sonification strategy see handleIncallSonification()
687 if (isStateInCall(oldState)) {
688 ALOGV("setPhoneState() in call state management: new state is %d", state);
689 for (size_t j = 0; j < mOutputs.size(); j++) {
690 audio_io_handle_t curOutput = mOutputs.keyAt(j);
691 for (int stream = 0; stream < AUDIO_STREAM_FOR_POLICY_CNT; stream++) {
692 handleIncallSonification((audio_stream_type_t)stream, false, true, curOutput);
693 }
694 }
695
696 // force reevaluating accessibility routing when call stops
697 mpClientInterface->invalidateStream(AUDIO_STREAM_ACCESSIBILITY);
698 }
699
700 /**
701 * Switching to or from incall state or switching between telephony and VoIP lead to force
702 * routing command.
703 */
704 bool force = ((is_state_in_call(oldState) != is_state_in_call(state))
705 || (is_state_in_call(state) && (state != oldState)));
706
707 // check for device and output changes triggered by new phone state
708 checkA2dpSuspend();
709 checkOutputForAllStrategies();
710 updateDevicesAndOutputs();
711
712 sp<SwAudioOutputDescriptor> hwOutputDesc = mPrimaryOutput;
713#ifdef VOICE_CONCURRENCY
714 char propValue[PROPERTY_VALUE_MAX];
715 bool prop_playback_enabled = false, prop_rec_enabled=false, prop_voip_enabled = false;
716
717 if(property_get("vendor.voice.playback.conc.disabled", propValue, NULL)) {
718 prop_playback_enabled = atoi(propValue) || !strncmp("true", propValue, 4);
719 }
720
721 if(property_get("vendor.voice.record.conc.disabled", propValue, NULL)) {
722 prop_rec_enabled = atoi(propValue) || !strncmp("true", propValue, 4);
723 }
724
725 if(property_get("vendor.voice.voip.conc.disabled", propValue, NULL)) {
726 prop_voip_enabled = atoi(propValue) || !strncmp("true", propValue, 4);
727 }
728
729 if ((AUDIO_MODE_IN_CALL != oldState) && (AUDIO_MODE_IN_CALL == state)) {
730 ALOGD("voice_conc:Entering to call mode oldState :: %d state::%d ",
731 oldState, state);
732 mvoice_call_state = state;
733 if (prop_rec_enabled) {
734 //Close all active inputs
735 Vector<sp <AudioInputDescriptor> > activeInputs = mInputs.getActiveInputs();
736 if (activeInputs.size() != 0) {
737 for (size_t i = 0; i < activeInputs.size(); i++) {
738 sp<AudioInputDescriptor> activeInput = activeInputs[i];
739 switch(activeInput->inputSource()) {
740 case AUDIO_SOURCE_VOICE_UPLINK:
741 case AUDIO_SOURCE_VOICE_DOWNLINK:
742 case AUDIO_SOURCE_VOICE_CALL:
743 ALOGD("voice_conc:FOUND active input during call active: %d",activeInput->inputSource());
744 break;
745
746 case AUDIO_SOURCE_VOICE_COMMUNICATION:
747 if(prop_voip_enabled) {
748 ALOGD("voice_conc:CLOSING VoIP input source on call setup :%d ",activeInput->inputSource());
749 AudioSessionCollection activeSessions = activeInput->getAudioSessions(true);
750 audio_session_t activeSession = activeSessions.keyAt(0);
751 stopInput(activeInput->mIoHandle, activeSession);
752 releaseInput(activeInput->mIoHandle, activeSession);
753 }
754 break;
755
756 default:
757 ALOGD("voice_conc:CLOSING input on call setup for inputSource: %d",activeInput->inputSource());
758 AudioSessionCollection activeSessions = activeInput->getAudioSessions(true);
759 audio_session_t activeSession = activeSessions.keyAt(0);
760 stopInput(activeInput->mIoHandle, activeSession);
761 releaseInput(activeInput->mIoHandle, activeSession);
762 break;
763 }
764 }
765 }
766 } else if (prop_voip_enabled) {
767 Vector<sp <AudioInputDescriptor> > activeInputs = mInputs.getActiveInputs();
768 if (activeInputs.size() != 0) {
769 for (size_t i = 0; i < activeInputs.size(); i++) {
770 sp<AudioInputDescriptor> activeInput = activeInputs[i];
771 if (AUDIO_SOURCE_VOICE_COMMUNICATION == activeInput->inputSource()) {
772 ALOGD("voice_conc:CLOSING VoIP on call setup : %d",activeInput->inputSource());
773 AudioSessionCollection activeSessions = activeInput->getAudioSessions(true);
774 audio_session_t activeSession = activeSessions.keyAt(0);
775 stopInput(activeInput->mIoHandle, activeSession);
776 releaseInput(activeInput->mIoHandle, activeSession);
777 }
778 }
779 }
780 }
781 if (prop_playback_enabled) {
782 // Move tracks associated to this strategy from previous output to new output
783 for (int i = AUDIO_STREAM_SYSTEM; i < AUDIO_STREAM_FOR_POLICY_CNT; i++) {
784 ALOGV("voice_conc:Invalidate on call mode for stream :: %d ", i);
785 if (AUDIO_OUTPUT_FLAG_DEEP_BUFFER == mFallBackflag) {
786 if ((AUDIO_STREAM_MUSIC == i) ||
787 (AUDIO_STREAM_VOICE_CALL == i) ) {
788 ALOGD("voice_conc:Invalidate stream type %d", i);
789 mpClientInterface->invalidateStream((audio_stream_type_t)i);
790 }
791 } else if (AUDIO_OUTPUT_FLAG_FAST == mFallBackflag) {
792 ALOGD("voice_conc:Invalidate stream type %d", i);
793 mpClientInterface->invalidateStream((audio_stream_type_t)i);
794 }
795 }
796 }
797
798 for (size_t i = 0; i < mOutputs.size(); i++) {
799 sp<SwAudioOutputDescriptor> outputDesc = mOutputs.valueAt(i);
800 if ( (outputDesc == NULL) || (outputDesc->mProfile == NULL)) {
801 ALOGD("voice_conc:ouput desc / profile is NULL");
802 continue;
803 }
804
805 bool isFastFallBackNeeded =
806 ((AUDIO_OUTPUT_FLAG_DEEP_BUFFER | AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD | AUDIO_OUTPUT_FLAG_DIRECT_PCM) & outputDesc->mProfile->getFlags());
807
808 if ((AUDIO_OUTPUT_FLAG_FAST == mFallBackflag) && isFastFallBackNeeded) {
809 if (((!outputDesc->isDuplicated() && outputDesc->mProfile->getFlags() & AUDIO_OUTPUT_FLAG_PRIMARY))
810 && prop_playback_enabled) {
811 ALOGD("voice_conc:calling suspendOutput on call mode for primary output");
812 mpClientInterface->suspendOutput(mOutputs.keyAt(i));
813 } //Close compress all sessions
814 else if ((outputDesc->mProfile->getFlags() & AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD)
815 && prop_playback_enabled) {
816 ALOGD("voice_conc:calling closeOutput on call mode for COMPRESS output");
817 closeOutput(mOutputs.keyAt(i));
818 }
819 else if ((outputDesc->mProfile->getFlags() & AUDIO_OUTPUT_FLAG_VOIP_RX)
820 && prop_voip_enabled) {
821 ALOGD("voice_conc:calling closeOutput on call mode for DIRECT output");
822 closeOutput(mOutputs.keyAt(i));
823 }
824 } else if (AUDIO_OUTPUT_FLAG_DEEP_BUFFER == mFallBackflag) {
825 if (outputDesc->mProfile->getFlags() & AUDIO_OUTPUT_FLAG_VOIP_RX) {
826 if (prop_voip_enabled) {
827 ALOGD("voice_conc:calling closeOutput on call mode for DIRECT output");
828 closeOutput(mOutputs.keyAt(i));
829 }
830 }
831 else if (prop_playback_enabled
832 && (outputDesc->mProfile->getFlags() & AUDIO_OUTPUT_FLAG_DIRECT)) {
833 ALOGD("voice_conc:calling closeOutput on call mode for COMPRESS output");
834 closeOutput(mOutputs.keyAt(i));
835 }
836 }
837 }
838 }
839
840 if ((AUDIO_MODE_IN_CALL == oldState || AUDIO_MODE_IN_COMMUNICATION == oldState) &&
841 (AUDIO_MODE_NORMAL == state) && prop_playback_enabled && mvoice_call_state) {
842 ALOGD("voice_conc:EXITING from call mode oldState :: %d state::%d \n",oldState, state);
843 mvoice_call_state = 0;
844 if (AUDIO_OUTPUT_FLAG_FAST == mFallBackflag) {
845 //restore PCM (deep-buffer) output after call termination
846 for (size_t i = 0; i < mOutputs.size(); i++) {
847 sp<SwAudioOutputDescriptor> outputDesc = mOutputs.valueAt(i);
848 if ( (outputDesc == NULL) || (outputDesc->mProfile == NULL)) {
849 ALOGD("voice_conc:ouput desc / profile is NULL");
850 continue;
851 }
852 if (!outputDesc->isDuplicated() && outputDesc->mProfile->getFlags() & AUDIO_OUTPUT_FLAG_PRIMARY) {
853 ALOGD("voice_conc:calling restoreOutput after call mode for primary output");
854 mpClientInterface->restoreOutput(mOutputs.keyAt(i));
855 }
856 }
857 }
858 //call invalidate tracks so that any open streams can fall back to deep buffer/compress path from ULL
859 for (int i = AUDIO_STREAM_SYSTEM; i < AUDIO_STREAM_FOR_POLICY_CNT; i++) {
860 ALOGV("voice_conc:Invalidate on call mode for stream :: %d ", i);
861 if (AUDIO_OUTPUT_FLAG_DEEP_BUFFER == mFallBackflag) {
862 if ((AUDIO_STREAM_MUSIC == i) ||
863 (AUDIO_STREAM_VOICE_CALL == i) ) {
864 mpClientInterface->invalidateStream((audio_stream_type_t)i);
865 }
866 } else if (AUDIO_OUTPUT_FLAG_FAST == mFallBackflag) {
867 mpClientInterface->invalidateStream((audio_stream_type_t)i);
868 }
869 }
870 }
871
872#endif
873
874 sp<SwAudioOutputDescriptor> outputDesc = NULL;
875 for (size_t i = 0; i < mOutputs.size(); i++) {
876 outputDesc = mOutputs.valueAt(i);
877 if ((outputDesc == NULL) || (outputDesc->mProfile == NULL)) {
878 ALOGD("voice_conc:ouput desc / profile is NULL");
879 continue;
880 }
881
882 if (property_get_bool("vendor.voice.dsd.playback.conc.disabled", true) &&
883 (outputDesc->mFlags & AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD) &&
884 (outputDesc->mFormat == AUDIO_FORMAT_DSD)) {
885 ALOGD("voice_conc:calling closeOutput on call mode for DSD COMPRESS output");
886 closeOutput(mOutputs.keyAt(i));
887 // call invalidate for music, so that DSD compress will fallback to deep-buffer.
888 mpClientInterface->invalidateStream(AUDIO_STREAM_MUSIC);
889 }
890
891 }
892
893#ifdef RECORD_PLAY_CONCURRENCY
894 char recConcPropValue[PROPERTY_VALUE_MAX];
895 bool prop_rec_play_enabled = false;
896
897 if (property_get("vendor.audio.rec.playback.conc.disabled", recConcPropValue, NULL)) {
898 prop_rec_play_enabled = atoi(recConcPropValue) || !strncmp("true", recConcPropValue, 4);
899 }
900 if (prop_rec_play_enabled) {
901 if (AUDIO_MODE_IN_COMMUNICATION == mEngine->getPhoneState()) {
902 ALOGD("phone state changed to MODE_IN_COMM invlaidating music and voice streams");
903 // call invalidate for voice streams, so that it can use deepbuffer with VoIP out device from HAL
904 mpClientInterface->invalidateStream(AUDIO_STREAM_VOICE_CALL);
905 // call invalidate for music, so that compress will fallback to deep-buffer with VoIP out device
906 mpClientInterface->invalidateStream(AUDIO_STREAM_MUSIC);
907
908 // close compress output to make sure session will be closed before timeout(60sec)
909 for (size_t i = 0; i < mOutputs.size(); i++) {
910
911 sp<SwAudioOutputDescriptor> outputDesc = mOutputs.valueAt(i);
912 if ((outputDesc == NULL) || (outputDesc->mProfile == NULL)) {
913 ALOGD("ouput desc / profile is NULL");
914 continue;
915 }
916
917 if (outputDesc->mProfile->getFlags() & AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD) {
918 ALOGD("calling closeOutput on call mode for COMPRESS output");
919 closeOutput(mOutputs.keyAt(i));
920 }
921 }
922 } else if ((oldState == AUDIO_MODE_IN_COMMUNICATION) &&
923 (mEngine->getPhoneState() == AUDIO_MODE_NORMAL)) {
924 // call invalidate for music so that music can fallback to compress
925 mpClientInterface->invalidateStream(AUDIO_STREAM_MUSIC);
926 }
927 }
928#endif
929 mPrevPhoneState = oldState;
930 int delayMs = 0;
931 if (isStateInCall(state)) {
932 nsecs_t sysTime = systemTime();
933 for (size_t i = 0; i < mOutputs.size(); i++) {
934 sp<SwAudioOutputDescriptor> desc = mOutputs.valueAt(i);
935 // mute media and sonification strategies and delay device switch by the largest
936 // latency of any output where either strategy is active.
937 // This avoid sending the ring tone or music tail into the earpiece or headset.
938 if ((isStrategyActive(desc, STRATEGY_MEDIA,
939 SONIFICATION_HEADSET_MUSIC_DELAY,
940 sysTime) ||
941 isStrategyActive(desc, STRATEGY_SONIFICATION,
942 SONIFICATION_HEADSET_MUSIC_DELAY,
943 sysTime)) &&
944 (delayMs < (int)desc->latency()*2)) {
945 delayMs = desc->latency()*2;
946 }
947 setStrategyMute(STRATEGY_MEDIA, true, desc);
948 setStrategyMute(STRATEGY_MEDIA, false, desc, MUTE_TIME_MS,
949 getDeviceForStrategy(STRATEGY_MEDIA, true /*fromCache*/));
950 setStrategyMute(STRATEGY_SONIFICATION, true, desc);
951 setStrategyMute(STRATEGY_SONIFICATION, false, desc, MUTE_TIME_MS,
952 getDeviceForStrategy(STRATEGY_SONIFICATION, true /*fromCache*/));
953 }
954 }
955
956 if (hasPrimaryOutput()) {
957 // Note that despite the fact that getNewOutputDevice() is called on the primary output,
958 // the device returned is not necessarily reachable via this output
959 audio_devices_t rxDevice = getNewOutputDevice(mPrimaryOutput, false /*fromCache*/);
960 // force routing command to audio hardware when ending call
961 // even if no device change is needed
962 if (isStateInCall(oldState) && rxDevice == AUDIO_DEVICE_NONE) {
963 rxDevice = mPrimaryOutput->device();
964 }
965
966 if (state == AUDIO_MODE_IN_CALL) {
967 updateCallRouting(rxDevice, delayMs);
968 } else if (oldState == AUDIO_MODE_IN_CALL) {
969 if (mCallRxPatch != 0) {
970 mpClientInterface->releaseAudioPatch(mCallRxPatch->mAfPatchHandle, 0);
971 mCallRxPatch.clear();
972 }
973 if (mCallTxPatch != 0) {
974 mpClientInterface->releaseAudioPatch(mCallTxPatch->mAfPatchHandle, 0);
975 mCallTxPatch.clear();
976 }
977 setOutputDevice(mPrimaryOutput, rxDevice, force, 0);
978 } else {
979 setOutputDevice(mPrimaryOutput, rxDevice, force, 0);
980 }
981 }
982 //update device for all non-primary outputs
983 for (size_t i = 0; i < mOutputs.size(); i++) {
984 audio_io_handle_t output = mOutputs.keyAt(i);
985 if (output != mPrimaryOutput->mIoHandle) {
986 newDevice = getNewOutputDevice(mOutputs.valueFor(output), false /*fromCache*/);
987 setOutputDevice(mOutputs.valueFor(output), newDevice, (newDevice != AUDIO_DEVICE_NONE));
988 }
989 }
990 // if entering in call state, handle special case of active streams
991 // pertaining to sonification strategy see handleIncallSonification()
992 if (isStateInCall(state)) {
993 ALOGV("setPhoneState() in call state management: new state is %d", state);
994 for (size_t j = 0; j < mOutputs.size(); j++) {
995 audio_io_handle_t curOutput = mOutputs.keyAt(j);
996 for (int stream = 0; stream < AUDIO_STREAM_FOR_POLICY_CNT; stream++) {
997 handleIncallSonification((audio_stream_type_t)stream, true, true, curOutput);
998 }
999 }
1000
1001 // force reevaluating accessibility routing when call starts
1002 mpClientInterface->invalidateStream(AUDIO_STREAM_ACCESSIBILITY);
1003 }
1004
1005 // Flag that ringtone volume must be limited to music volume until we exit MODE_RINGTONE
1006 if (state == AUDIO_MODE_RINGTONE &&
1007 isStreamActive(AUDIO_STREAM_MUSIC, SONIFICATION_HEADSET_MUSIC_DELAY)) {
1008 mLimitRingtoneVolume = true;
1009 } else {
1010 mLimitRingtoneVolume = false;
1011 }
1012}
1013
1014void AudioPolicyManagerCustom::setForceUse(audio_policy_force_use_t usage,
1015 audio_policy_forced_cfg_t config)
1016{
1017 ALOGD("setForceUse() usage %d, config %d, mPhoneState %d", usage, config, mEngine->getPhoneState());
1018 if (config == mEngine->getForceUse(usage)) {
1019 return;
1020 }
1021
1022 if (mEngine->setForceUse(usage, config) != NO_ERROR) {
1023 ALOGW("setForceUse() could not set force cfg %d for usage %d", config, usage);
1024 return;
1025 }
1026 bool forceVolumeReeval = (usage == AUDIO_POLICY_FORCE_FOR_COMMUNICATION) ||
1027 (usage == AUDIO_POLICY_FORCE_FOR_DOCK) ||
1028 (usage == AUDIO_POLICY_FORCE_FOR_SYSTEM);
1029
1030 // check for device and output changes triggered by new force usage
1031 checkA2dpSuspend();
1032 checkOutputForAllStrategies();
1033 updateDevicesAndOutputs();
1034
1035 /*audio policy: workaround for truncated touch sounds*/
1036 //FIXME: workaround for truncated touch sounds
1037 // to be removed when the problem is handled by system UI
1038 uint32_t delayMs = 0;
1039 uint32_t waitMs = 0;
1040 if (usage == AUDIO_POLICY_FORCE_FOR_COMMUNICATION) {
1041 delayMs = TOUCH_SOUND_FIXED_DELAY_MS;
1042 }
1043 if (mEngine->getPhoneState() == AUDIO_MODE_IN_CALL && hasPrimaryOutput()) {
1044 audio_devices_t newDevice = getNewOutputDevice(mPrimaryOutput, true /*fromCache*/);
kunleiz42b6d4c2018-10-03 09:27:38 +02001045 if (forceVolumeReeval && (newDevice != AUDIO_DEVICE_NONE)) {
1046 applyStreamVolumes(mPrimaryOutput, newDevice, delayMs, true);
1047 }
Marko Manef8d7e42018-08-26 23:20:31 +02001048 waitMs = updateCallRouting(newDevice, delayMs);
1049 }
1050 // Use reverse loop to make sure any low latency usecases (generally tones)
1051 // are not routed before non LL usecases (generally music).
1052 // We can safely assume that LL output would always have lower index,
1053 // and use this work-around to avoid routing of output with music stream
1054 // from the context of short lived LL output.
1055 // Note: in case output's share backend(HAL sharing is implicit) all outputs
1056 // gets routing update while processing first output itself.
1057 for (size_t i = mOutputs.size(); i > 0; i--) {
1058 sp<SwAudioOutputDescriptor> outputDesc = mOutputs.valueAt(i-1);
1059 audio_devices_t newDevice = getNewOutputDevice(outputDesc, true /*fromCache*/);
1060 if ((mEngine->getPhoneState() != AUDIO_MODE_IN_CALL) || (outputDesc != mPrimaryOutput)) {
1061 waitMs = setOutputDevice(outputDesc, newDevice, (newDevice != AUDIO_DEVICE_NONE),
1062 delayMs);
kunleiz42b6d4c2018-10-03 09:27:38 +02001063
1064 if (forceVolumeReeval && (newDevice != AUDIO_DEVICE_NONE)) {
1065 applyStreamVolumes(outputDesc, newDevice, waitMs, true);
1066 }
1067 }
Marko Manef8d7e42018-08-26 23:20:31 +02001068 }
1069
1070 Vector<sp <AudioInputDescriptor> > activeInputs = mInputs.getActiveInputs();
1071 for (size_t i = 0; i < activeInputs.size(); i++) {
1072 sp<AudioInputDescriptor> activeDesc = activeInputs[i];
1073 audio_devices_t newDevice = getNewInputDevice(activeDesc);
1074 // Force new input selection if the new device can not be reached via current input
1075 if (activeDesc->mProfile->getSupportedDevices().types() &
1076 (newDevice & ~AUDIO_DEVICE_BIT_IN)) {
1077 setInputDevice(activeDesc->mIoHandle, newDevice);
1078 } else {
1079 closeInput(activeDesc->mIoHandle);
1080 }
1081 }
1082}
1083
1084status_t AudioPolicyManagerCustom::stopSource(const sp<AudioOutputDescriptor>& outputDesc,
1085 audio_stream_type_t stream,
1086 bool forceDeviceUpdate)
1087{
1088 if (stream < 0 || stream >= AUDIO_STREAM_CNT) {
1089 ALOGW("stopSource() invalid stream %d", stream);
1090 return INVALID_OPERATION;
1091 }
1092 // always handle stream stop, check which stream type is stopping
1093 handleEventForBeacon(stream == AUDIO_STREAM_TTS ? STOPPING_BEACON : STOPPING_OUTPUT);
1094
1095 // handle special case for sonification while in call
1096 if (isInCall()) {
1097 if (outputDesc->isDuplicated()) {
1098 handleIncallSonification(stream, false, false, outputDesc->subOutput1()->mIoHandle);
1099 handleIncallSonification(stream, false, false, outputDesc->subOutput2()->mIoHandle);
1100 }
1101 handleIncallSonification(stream, false, false, outputDesc->mIoHandle);
1102 }
1103
1104 if (outputDesc->mRefCount[stream] > 0) {
1105 // decrement usage count of this stream on the output
1106 outputDesc->changeRefCount(stream, -1);
1107
1108 // store time at which the stream was stopped - see isStreamActive()
1109 if (outputDesc->mRefCount[stream] == 0 || forceDeviceUpdate) {
1110 outputDesc->mStopTime[stream] = systemTime();
1111 audio_devices_t prevDevice = outputDesc->device();
1112 audio_devices_t newDevice = getNewOutputDevice(outputDesc, false /*fromCache*/);
1113 // delay the device switch by twice the latency because stopOutput() is executed when
1114 // the track stop() command is received and at that time the audio track buffer can
1115 // still contain data that needs to be drained. The latency only covers the audio HAL
1116 // and kernel buffers. Also the latency does not always include additional delay in the
1117 // audio path (audio DSP, CODEC ...)
1118 setOutputDevice(outputDesc, newDevice, false, outputDesc->latency()*2);
1119
1120 // force restoring the device selection on other active outputs if it differs from the
1121 // one being selected for this output
1122 for (size_t i = 0; i < mOutputs.size(); i++) {
1123 audio_io_handle_t curOutput = mOutputs.keyAt(i);
1124 sp<AudioOutputDescriptor> desc = mOutputs.valueAt(i);
1125 if (desc != outputDesc &&
1126 desc->isActive() &&
1127 outputDesc->sharesHwModuleWith(desc) &&
1128 (newDevice != desc->device())) {
1129 audio_devices_t dev = getNewOutputDevice(mOutputs.valueFor(curOutput), false /*fromCache*/);
1130 bool force = prevDevice != dev;
1131 uint32_t delayMs;
1132 if (dev == prevDevice) {
1133 delayMs = 0;
1134 } else {
1135 delayMs = outputDesc->latency()*2;
1136 }
1137 setOutputDevice(desc,
1138 dev,
1139 force,
1140 delayMs);
1141 /*audio policy: fix media volume after ringtone*/
1142 // re-apply device specific volume if not done by setOutputDevice()
1143 if (!force) {
1144 applyStreamVolumes(desc, dev, delayMs);
1145 }
1146 }
1147 }
1148 // update the outputs if stopping one with a stream that can affect notification routing
1149 handleNotificationRoutingForStream(stream);
1150 }
1151 if (stream == AUDIO_STREAM_MUSIC) {
1152 selectOutputForMusicEffects();
1153 }
1154 return NO_ERROR;
1155 } else {
1156 ALOGW("stopOutput() refcount is already 0");
1157 return INVALID_OPERATION;
1158 }
1159}
1160
1161status_t AudioPolicyManagerCustom::startSource(const sp<AudioOutputDescriptor>& outputDesc,
1162 audio_stream_type_t stream,
1163 audio_devices_t device,
1164 const char *address,
1165 uint32_t *delayMs)
1166{
1167 // cannot start playback of STREAM_TTS if any other output is being used
1168 uint32_t beaconMuteLatency = 0;
1169
1170 if (stream < 0 || stream >= AUDIO_STREAM_CNT) {
1171 ALOGW("startSource() invalid stream %d", stream);
1172 return INVALID_OPERATION;
1173 }
1174
1175 *delayMs = 0;
1176 if (stream == AUDIO_STREAM_TTS) {
1177 ALOGV("\t found BEACON stream");
1178 if (!mTtsOutputAvailable && mOutputs.isAnyOutputActive(AUDIO_STREAM_TTS /*streamToIgnore*/)) {
1179 return INVALID_OPERATION;
1180 } else {
1181 beaconMuteLatency = handleEventForBeacon(STARTING_BEACON);
1182 }
1183 } else {
1184 // some playback other than beacon starts
1185 beaconMuteLatency = handleEventForBeacon(STARTING_OUTPUT);
1186 }
1187
1188 // force device change if the output is inactive and no audio patch is already present.
1189 // check active before incrementing usage count
1190 bool force = !outputDesc->isActive() &&
1191 (outputDesc->getPatchHandle() == AUDIO_PATCH_HANDLE_NONE);
1192
1193 // increment usage count for this stream on the requested output:
1194 // NOTE that the usage count is the same for duplicated output and hardware output which is
1195 // necessary for a correct control of hardware output routing by startOutput() and stopOutput()
1196 outputDesc->changeRefCount(stream, 1);
1197
1198 if (stream == AUDIO_STREAM_MUSIC) {
1199 selectOutputForMusicEffects();
1200 }
1201
1202 if (outputDesc->mRefCount[stream] == 1 || device != AUDIO_DEVICE_NONE) {
1203 // starting an output being rerouted?
1204 if (device == AUDIO_DEVICE_NONE) {
1205 device = getNewOutputDevice(outputDesc, false /*fromCache*/);
1206 }
1207 routing_strategy strategy = getStrategy(stream);
1208 bool shouldWait = (strategy == STRATEGY_SONIFICATION) ||
1209 (strategy == STRATEGY_SONIFICATION_RESPECTFUL) ||
1210 (beaconMuteLatency > 0);
1211 uint32_t waitMs = beaconMuteLatency;
1212 for (size_t i = 0; i < mOutputs.size(); i++) {
1213 sp<AudioOutputDescriptor> desc = mOutputs.valueAt(i);
1214 if (desc != outputDesc) {
1215 // force a device change if any other output is:
1216 // - managed by the same hw module
1217 // - has a current device selection that differs from selected device.
1218 // - supports currently selected device
1219 // - has an active audio patch
1220 // In this case, the audio HAL must receive the new device selection so that it can
1221 // change the device currently selected by the other active output.
1222 if (outputDesc->sharesHwModuleWith(desc) &&
1223 desc->device() != device &&
1224 desc->supportedDevices() & device &&
1225 desc->getPatchHandle() != AUDIO_PATCH_HANDLE_NONE) {
1226 force = true;
1227 }
1228 // wait for audio on other active outputs to be presented when starting
1229 // a notification so that audio focus effect can propagate, or that a mute/unmute
1230 // event occurred for beacon
1231 uint32_t latency = desc->latency();
1232 if (shouldWait && desc->isActive(latency * 2) && (waitMs < latency)) {
1233 waitMs = latency;
1234 }
1235 }
1236 }
1237 uint32_t muteWaitMs = setOutputDevice(outputDesc, device, force, 0, NULL, address);
1238
1239 // handle special case for sonification while in call
1240 if (isInCall()) {
1241 handleIncallSonification(stream, true, false, outputDesc->mIoHandle);
1242 }
1243
1244 // apply volume rules for current stream and device if necessary
1245 checkAndSetVolume(stream,
1246 mVolumeCurves->getVolumeIndex(stream, device),
1247 outputDesc,
1248 device);
1249
1250 // update the outputs if starting an output with a stream that can affect notification
1251 // routing
1252 handleNotificationRoutingForStream(stream);
1253
1254 // force reevaluating accessibility routing when ringtone or alarm starts
1255 if (strategy == STRATEGY_SONIFICATION) {
1256 mpClientInterface->invalidateStream(AUDIO_STREAM_ACCESSIBILITY);
1257 }
1258 if (waitMs > muteWaitMs) {
1259 *delayMs = waitMs - muteWaitMs;
1260 }
1261
1262 } else {
1263 // handle special case for sonification while in call
1264 if (isInCall()) {
1265 handleIncallSonification(stream, true, false, outputDesc->mIoHandle);
1266 }
1267 }
1268 return NO_ERROR;
1269}
1270
1271void AudioPolicyManagerCustom::handleIncallSonification(audio_stream_type_t stream,
1272 bool starting, bool stateChange,
1273 audio_io_handle_t output)
1274{
1275 if(!hasPrimaryOutput()) {
1276 return;
1277 }
1278 // no action needed for AUDIO_STREAM_PATCH stream type, it's for internal flinger tracks
1279 if (stream == AUDIO_STREAM_PATCH) {
1280 return;
1281 }
1282 // if the stream pertains to sonification strategy and we are in call we must
1283 // mute the stream if it is low visibility. If it is high visibility, we must play a tone
1284 // in the device used for phone strategy and play the tone if the selected device does not
1285 // interfere with the device used for phone strategy
1286 // if stateChange is true, we are called from setPhoneState() and we must mute or unmute as
1287 // many times as there are active tracks on the output
1288 const routing_strategy stream_strategy = getStrategy(stream);
1289 if ((stream_strategy == STRATEGY_SONIFICATION) ||
1290 ((stream_strategy == STRATEGY_SONIFICATION_RESPECTFUL))) {
1291 sp<SwAudioOutputDescriptor> outputDesc = mOutputs.valueFor(output);
1292 ALOGV("handleIncallSonification() stream %d starting %d device %x stateChange %d",
1293 stream, starting, outputDesc->mDevice, stateChange);
1294 if (outputDesc->mRefCount[stream]) {
1295 int muteCount = 1;
1296 if (stateChange) {
1297 muteCount = outputDesc->mRefCount[stream];
1298 }
1299 if (audio_is_low_visibility(stream)) {
1300 ALOGV("handleIncallSonification() low visibility, muteCount %d", muteCount);
1301 for (int i = 0; i < muteCount; i++) {
1302 setStreamMute(stream, starting, outputDesc);
1303 }
1304 } else {
1305 ALOGV("handleIncallSonification() high visibility");
1306 if (outputDesc->device() &
1307 getDeviceForStrategy(STRATEGY_PHONE, true /*fromCache*/)) {
1308 ALOGV("handleIncallSonification() high visibility muted, muteCount %d", muteCount);
1309 for (int i = 0; i < muteCount; i++) {
1310 setStreamMute(stream, starting, outputDesc);
1311 }
1312 }
1313 if (starting) {
1314 mpClientInterface->startTone(AUDIO_POLICY_TONE_IN_CALL_NOTIFICATION,
1315 AUDIO_STREAM_VOICE_CALL);
1316 } else {
1317 mpClientInterface->stopTone();
1318 }
1319 }
1320 }
1321 }
1322}
1323
1324void AudioPolicyManagerCustom::handleNotificationRoutingForStream(audio_stream_type_t stream) {
1325 switch(stream) {
1326 case AUDIO_STREAM_MUSIC:
1327 checkOutputForStrategy(STRATEGY_SONIFICATION_RESPECTFUL);
1328 updateDevicesAndOutputs();
1329 break;
1330 default:
1331 break;
1332 }
1333}
1334
1335status_t AudioPolicyManagerCustom::checkAndSetVolume(audio_stream_type_t stream,
1336 int index,
1337 const sp<AudioOutputDescriptor>& outputDesc,
1338 audio_devices_t device,
1339 int delayMs,
1340 bool force)
1341{
1342 if (stream < 0 || stream >= AUDIO_STREAM_CNT) {
1343 ALOGW("checkAndSetVolume() invalid stream %d", stream);
1344 return INVALID_OPERATION;
1345 }
1346 // do not change actual stream volume if the stream is muted
1347 if (outputDesc->mMuteCount[stream] != 0) {
1348 ALOGVV("checkAndSetVolume() stream %d muted count %d",
1349 stream, outputDesc->mMuteCount[stream]);
1350 return NO_ERROR;
1351 }
1352 audio_policy_forced_cfg_t forceUseForComm =
1353 mEngine->getForceUse(AUDIO_POLICY_FORCE_FOR_COMMUNICATION);
1354 // do not change in call volume if bluetooth is connected and vice versa
1355 if ((stream == AUDIO_STREAM_VOICE_CALL && forceUseForComm == AUDIO_POLICY_FORCE_BT_SCO) ||
1356 (stream == AUDIO_STREAM_BLUETOOTH_SCO && forceUseForComm != AUDIO_POLICY_FORCE_BT_SCO)) {
1357 ALOGV("checkAndSetVolume() cannot set stream %d volume with force use = %d for comm",
1358 stream, forceUseForComm);
1359 return INVALID_OPERATION;
1360 }
1361
1362 if (device == AUDIO_DEVICE_NONE) {
1363 device = outputDesc->device();
1364 }
1365
1366 float volumeDb = computeVolume(stream, index, device);
1367 if (outputDesc->isFixedVolume(device)) {
1368 volumeDb = 0.0f;
1369 }
1370
1371 outputDesc->setVolume(volumeDb, stream, device, delayMs, force);
1372
1373 if (stream == AUDIO_STREAM_VOICE_CALL ||
1374 stream == AUDIO_STREAM_BLUETOOTH_SCO) {
1375 float voiceVolume;
1376 // Force voice volume to max for bluetooth SCO as volume is managed by the headset
1377 if (stream == AUDIO_STREAM_VOICE_CALL) {
1378 voiceVolume = (float)index/(float)mVolumeCurves->getVolumeIndexMax(stream);
1379 } else {
1380 voiceVolume = 1.0;
1381 }
1382
1383 if (voiceVolume != mLastVoiceVolume) {
1384 mpClientInterface->setVoiceVolume(voiceVolume, delayMs);
1385 mLastVoiceVolume = voiceVolume;
1386 }
1387#ifdef FM_POWER_OPT
1388 } else if (stream == AUDIO_STREAM_MUSIC && hasPrimaryOutput() &&
1389 outputDesc == mPrimaryOutput && mFMIsActive) {
1390 /* Avoid unnecessary set_parameter calls as it puts the primary
1391 outputs FastMixer in HOT_IDLE leading to breaks in audio */
1392 if (volumeDb != mPrevFMVolumeDb) {
1393 mPrevFMVolumeDb = volumeDb;
1394 AudioParameter param = AudioParameter();
1395 param.addFloat(String8("fm_volume"), Volume::DbToAmpl(volumeDb));
1396 //Double delayMs to avoid sound burst while device switch.
1397 mpClientInterface->setParameters(mPrimaryOutput->mIoHandle, param.toString(), delayMs*2);
1398 }
1399#endif /* FM_POWER_OPT end */
1400 }
1401
1402 return NO_ERROR;
1403}
1404
1405bool AudioPolicyManagerCustom::isDirectOutput(audio_io_handle_t output) {
1406 for (size_t i = 0; i < mOutputs.size(); i++) {
1407 audio_io_handle_t curOutput = mOutputs.keyAt(i);
1408 sp<SwAudioOutputDescriptor> desc = mOutputs.valueAt(i);
1409 if ((curOutput == output) && (desc->mFlags & AUDIO_OUTPUT_FLAG_DIRECT)) {
1410 return true;
1411 }
1412 }
1413 return false;
1414}
1415
1416bool static tryForDirectPCM(audio_output_flags_t flags)
1417{
1418 bool trackDirectPCM = false; // Output request for track created by other apps
1419
1420 if (flags == AUDIO_OUTPUT_FLAG_NONE) {
1421 trackDirectPCM = property_get_bool("vendor.audio.offload.track.enable", true);
1422 }
1423 return trackDirectPCM;
1424}
1425
1426status_t AudioPolicyManagerCustom::getOutputForAttr(const audio_attributes_t *attr,
1427 audio_io_handle_t *output,
1428 audio_session_t session,
1429 audio_stream_type_t *stream,
1430 uid_t uid,
1431 const audio_config_t *config,
1432 audio_output_flags_t *flags,
1433 audio_port_handle_t *selectedDeviceId,
1434 audio_port_handle_t *portId)
1435{
1436 audio_offload_info_t tOffloadInfo = AUDIO_INFO_INITIALIZER;
1437 audio_config_t tConfig;
1438
1439 uint32_t bitWidth = (audio_bytes_per_sample(config->format) * 8);
1440
1441 memcpy(&tConfig, config, sizeof(audio_config_t));
1442 if ((*flags == AUDIO_OUTPUT_FLAG_DIRECT || tryForDirectPCM(*flags)) &&
1443 (!memcmp(&config->offload_info, &tOffloadInfo, sizeof(audio_offload_info_t)))) {
1444 tConfig.offload_info.sample_rate = config->sample_rate;
1445 tConfig.offload_info.channel_mask = config->channel_mask;
1446 tConfig.offload_info.format = config->format;
1447 tConfig.offload_info.stream_type = *stream;
1448 tConfig.offload_info.bit_width = bitWidth;
1449 if (attr != NULL) {
1450 ALOGV("found attribute .. setting usage %d ", attr->usage);
1451 tConfig.offload_info.usage = attr->usage;
1452 } else {
1453 ALOGI("%s:: attribute is NULL .. no usage set", __func__);
1454 }
1455 }
1456
1457 return AudioPolicyManager::getOutputForAttr(attr, output, session, stream,
1458 (uid_t)uid, &tConfig,
1459 flags,
1460 (audio_port_handle_t*)selectedDeviceId,
1461 portId);
1462}
1463
1464audio_io_handle_t AudioPolicyManagerCustom::getOutputForDevice(
1465 audio_devices_t device,
1466 audio_session_t session,
1467 audio_stream_type_t stream,
1468 const audio_config_t *config,
1469 audio_output_flags_t *flags)
1470{
1471 audio_io_handle_t output = AUDIO_IO_HANDLE_NONE;
1472 status_t status;
1473
1474 if (stream < AUDIO_STREAM_MIN || stream >= AUDIO_STREAM_CNT) {
1475 ALOGE("%s: invalid stream %d", __func__, stream);
1476 return AUDIO_IO_HANDLE_NONE;
1477 }
1478
1479 if (((*flags & AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD) != 0) &&
1480 (stream != AUDIO_STREAM_MUSIC)) {
1481 // compress should not be used for non-music streams
1482 ALOGE("Offloading only allowed with music stream");
1483 return 0;
1484 }
1485
1486#ifdef COMPRESS_VOIP_ENABLED
1487 if ((mEngine->getPhoneState() == AUDIO_MODE_IN_COMMUNICATION) &&
1488 (stream == AUDIO_STREAM_VOICE_CALL) &&
1489 audio_is_linear_pcm(config->format)) {
1490 // let voice stream to go with primary output by default
1491 // in case direct voip is bypassed
1492 bool use_primary_out = true;
1493
1494 if ((config->channel_mask == 1) &&
1495 (config->sample_rate == 8000 || config->sample_rate == 16000 ||
1496 config->sample_rate == 32000 || config->sample_rate == 48000)) {
1497 // Allow Voip direct output only if:
1498 // audio mode is MODE_IN_COMMUNCATION; AND
1499 // voip output is not opened already; AND
1500 // requested sample rate matches with that of voip input stream (if opened already)
1501 int value = 0;
1502 uint32_t voipOutCount = 1, voipSampleRate = 1;
1503
1504 String8 valueStr = mpClientInterface->getParameters((audio_io_handle_t)0,
1505 String8("voip_out_stream_count"));
1506 AudioParameter result = AudioParameter(valueStr);
1507 if (result.getInt(String8("voip_out_stream_count"), value) == NO_ERROR) {
1508 voipOutCount = value;
1509 }
1510
1511 valueStr = mpClientInterface->getParameters((audio_io_handle_t)0,
1512 String8("voip_sample_rate"));
1513 result = AudioParameter(valueStr);
1514 if (result.getInt(String8("voip_sample_rate"), value) == NO_ERROR) {
1515 voipSampleRate = value;
1516 }
1517
1518 if ((voipOutCount == 0) &&
1519 ((voipSampleRate == 0) || (voipSampleRate == config->sample_rate))) {
1520 char propValue[PROPERTY_VALUE_MAX] = {0};
1521 property_get("vendor.voice.path.for.pcm.voip", propValue, "0");
1522 bool voipPcmSysPropEnabled = !strncmp("true", propValue, sizeof("true"));
1523 if (voipPcmSysPropEnabled && (config->format == AUDIO_FORMAT_PCM_16_BIT)) {
1524 *flags = (audio_output_flags_t)(AUDIO_OUTPUT_FLAG_VOIP_RX |
1525 AUDIO_OUTPUT_FLAG_DIRECT);
1526 ALOGD("Set VoIP and Direct output flags for PCM format");
1527 use_primary_out = false;
1528 }
1529 }
1530 }
1531
1532 if (use_primary_out) {
1533 *flags = (audio_output_flags_t)(AUDIO_OUTPUT_FLAG_FAST|AUDIO_OUTPUT_FLAG_PRIMARY);
1534 }
1535#else
1536 if (mEngine->getPhoneState() == AUDIO_MODE_IN_COMMUNICATION &&
1537 stream == AUDIO_STREAM_VOICE_CALL &&
1538 audio_is_linear_pcm(config->format)) {
1539 //check if VoIP output is not opened already
1540 bool voip_pcm_already_in_use = false;
1541 for (size_t i = 0; i < mOutputs.size(); i++) {
1542 sp<SwAudioOutputDescriptor> desc = mOutputs.valueAt(i);
1543 if (desc->mFlags == (AUDIO_OUTPUT_FLAG_VOIP_RX | AUDIO_OUTPUT_FLAG_DIRECT)) {
1544 //close voip output if currently open by the same client with different device
1545 if (desc->mDirectClientSession == session &&
1546 desc->device() != device) {
1547 closeOutput(desc->mIoHandle);
1548 } else {
1549 voip_pcm_already_in_use = true;
1550 ALOGD("VoIP PCM already in use");
1551 }
1552 break;
1553 }
1554 }
1555
1556 if (!voip_pcm_already_in_use) {
1557 *flags = (audio_output_flags_t)(AUDIO_OUTPUT_FLAG_VOIP_RX |
1558 AUDIO_OUTPUT_FLAG_DIRECT);
1559 ALOGV("Set VoIP and Direct output flags for PCM format");
1560 }
1561#endif
1562 //IF VOIP is going to be started at the same time as when
1563 //vr is enabled, get VOIP to fallback to low latency
1564 String8 vr_value;
1565 String8 value_Str;
1566 bool is_vr_mode_on = false;
1567 AudioParameter ret;
1568
1569 value_Str = mpClientInterface->getParameters((audio_io_handle_t)0,
1570 String8("vr_audio_mode_on"));
1571 ret = AudioParameter(value_Str);
1572 if (ret.get(String8("vr_audio_mode_on"), vr_value) == NO_ERROR) {
1573 is_vr_mode_on = vr_value.contains("true");
1574 ALOGI("VR mode is %d, switch to primary output if request is for fast|raw",
1575 is_vr_mode_on);
1576 }
1577
1578 if (is_vr_mode_on) {
1579 //check the flags being requested for, and clear FAST|RAW
1580 *flags = (audio_output_flags_t)(*flags &
1581 (~(AUDIO_OUTPUT_FLAG_FAST|AUDIO_OUTPUT_FLAG_RAW)));
1582
1583 }
1584
1585 }
1586
1587#ifdef VOICE_CONCURRENCY
1588 char propValue[PROPERTY_VALUE_MAX];
1589 bool prop_play_enabled=false, prop_voip_enabled = false;
1590
1591 if(property_get("vendor.voice.playback.conc.disabled", propValue, NULL)) {
1592 prop_play_enabled = atoi(propValue) || !strncmp("true", propValue, 4);
1593 }
1594
1595 if(property_get("vendor.voice.voip.conc.disabled", propValue, NULL)) {
1596 prop_voip_enabled = atoi(propValue) || !strncmp("true", propValue, 4);
1597 }
1598
1599 bool isDeepBufferFallBackNeeded =
1600 ((AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD | AUDIO_OUTPUT_FLAG_DIRECT_PCM) & *flags);
1601 bool isFastFallBackNeeded =
1602 ((AUDIO_OUTPUT_FLAG_DEEP_BUFFER | AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD | AUDIO_OUTPUT_FLAG_DIRECT_PCM) & *flags);
1603
1604 if (prop_play_enabled && mvoice_call_state) {
1605 //check if voice call is active / running in background
1606 if((AUDIO_MODE_IN_CALL == mEngine->getPhoneState()) ||
1607 ((AUDIO_MODE_IN_CALL == mPrevPhoneState)
1608 && (AUDIO_MODE_IN_COMMUNICATION == mEngine->getPhoneState())))
1609 {
1610 if(AUDIO_OUTPUT_FLAG_VOIP_RX & *flags) {
1611 if(prop_voip_enabled) {
1612 ALOGD("voice_conc:getoutput:IN call mode return no o/p for VoIP %x",
1613 *flags );
1614 return 0;
1615 }
1616 }
1617 else {
1618 if (isFastFallBackNeeded &&
1619 (AUDIO_OUTPUT_FLAG_FAST == mFallBackflag)) {
1620 ALOGD("voice_conc:IN call mode adding ULL flags .. flags: %x ", *flags );
1621 *flags = AUDIO_OUTPUT_FLAG_FAST;
1622 } else if (isDeepBufferFallBackNeeded &&
1623 (AUDIO_OUTPUT_FLAG_DEEP_BUFFER == mFallBackflag)) {
1624 if (AUDIO_STREAM_MUSIC == stream) {
1625 *flags = AUDIO_OUTPUT_FLAG_DEEP_BUFFER;
1626 ALOGD("voice_conc:IN call mode adding deep-buffer flags %x ", *flags );
1627 }
1628 else {
1629 *flags = AUDIO_OUTPUT_FLAG_FAST;
1630 ALOGD("voice_conc:IN call mode adding fast flags %x ", *flags );
1631 }
1632 }
1633 }
1634 }
1635 } else if (prop_voip_enabled && mvoice_call_state) {
1636 //check if voice call is active / running in background
1637 //some of VoIP apps(like SIP2SIP call) supports resume of VoIP call when call in progress
1638 //return only ULL ouput
1639 if((AUDIO_MODE_IN_CALL == mEngine->getPhoneState()) ||
1640 ((AUDIO_MODE_IN_CALL == mPrevPhoneState)
1641 && (AUDIO_MODE_IN_COMMUNICATION == mEngine->getPhoneState())))
1642 {
1643 if(AUDIO_OUTPUT_FLAG_VOIP_RX & *flags) {
1644 ALOGD("voice_conc:getoutput:IN call mode return no o/p for VoIP %x",
1645 *flags );
1646 return 0;
1647 }
1648 }
1649 }
1650#endif
1651#ifdef RECORD_PLAY_CONCURRENCY
1652 char recConcPropValue[PROPERTY_VALUE_MAX];
1653 bool prop_rec_play_enabled = false;
1654
1655 if (property_get("vendor.audio.rec.playback.conc.disabled", recConcPropValue, NULL)) {
1656 prop_rec_play_enabled = atoi(recConcPropValue) || !strncmp("true", recConcPropValue, 4);
1657 }
1658 if ((prop_rec_play_enabled) &&
1659 ((true == mIsInputRequestOnProgress) || (mInputs.activeInputsCountOnDevices() > 0))) {
1660 if (AUDIO_MODE_IN_COMMUNICATION == mEngine->getPhoneState()) {
1661 if (AUDIO_OUTPUT_FLAG_VOIP_RX & *flags) {
1662 // allow VoIP using voice path
1663 // Do nothing
1664 } else if((*flags & AUDIO_OUTPUT_FLAG_FAST) == 0) {
1665 ALOGD("voice_conc:MODE_IN_COMM is setforcing deep buffer output for non ULL... flags: %x", *flags);
1666 // use deep buffer path for all non ULL outputs
1667 *flags = AUDIO_OUTPUT_FLAG_DEEP_BUFFER;
1668 }
1669 } else if ((*flags & AUDIO_OUTPUT_FLAG_FAST) == 0) {
1670 ALOGD("voice_conc:Record mode is on forcing deep buffer output for non ULL... flags: %x ", *flags);
1671 // use deep buffer path for all non ULL outputs
1672 *flags = AUDIO_OUTPUT_FLAG_DEEP_BUFFER;
1673 }
1674 }
1675 if (prop_rec_play_enabled &&
1676 (stream == AUDIO_STREAM_ENFORCED_AUDIBLE)) {
1677 ALOGD("Record conc is on forcing ULL output for ENFORCED_AUDIBLE");
1678 *flags = AUDIO_OUTPUT_FLAG_FAST;
1679 }
1680#endif
1681
1682#ifdef AUDIO_EXTN_AFE_PROXY_ENABLED
1683 /*
1684 * WFD audio routes back to target speaker when starting a ringtone playback.
1685 * This is because primary output is reused for ringtone, so output device is
1686 * updated based on SONIFICATION strategy for both ringtone and music playback.
1687 * The same issue is not seen on remoted_submix HAL based WFD audio because
1688 * primary output is not reused and a new output is created for ringtone playback.
1689 * Issue is fixed by updating output flag to AUDIO_OUTPUT_FLAG_FAST when there is
1690 * a non-music stream playback on WFD, so primary output is not reused for ringtone.
1691 */
1692 audio_devices_t availableOutputDeviceTypes = mAvailableOutputDevices.types();
1693 if ((availableOutputDeviceTypes & AUDIO_DEVICE_OUT_PROXY)
1694 && (stream != AUDIO_STREAM_MUSIC)) {
1695 ALOGD("WFD audio: use OUTPUT_FLAG_FAST for non music stream. flags:%x", *flags );
1696 //For voip paths
1697 if (*flags & AUDIO_OUTPUT_FLAG_DIRECT)
1698 *flags = AUDIO_OUTPUT_FLAG_DIRECT;
1699 else //route every thing else to ULL path
1700 *flags = AUDIO_OUTPUT_FLAG_FAST;
1701 }
1702#endif
1703
1704 // open a direct output if required by specified parameters
1705 // force direct flag if offload flag is set: offloading implies a direct output stream
1706 // and all common behaviors are driven by checking only the direct flag
1707 // this should normally be set appropriately in the policy configuration file
1708 if ((*flags & AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD) != 0) {
1709 *flags = (audio_output_flags_t)(*flags | AUDIO_OUTPUT_FLAG_DIRECT);
1710 }
1711 if ((*flags & AUDIO_OUTPUT_FLAG_HW_AV_SYNC) != 0) {
1712 *flags = (audio_output_flags_t)(*flags | AUDIO_OUTPUT_FLAG_DIRECT);
1713 }
1714
1715 // Do internal direct magic here
1716 bool offload_disabled = property_get_bool("audio.offload.disable", false);
1717 if ((*flags == AUDIO_OUTPUT_FLAG_NONE) &&
1718 (stream == AUDIO_STREAM_MUSIC) &&
1719 ( !offload_disabled) &&
1720 ((config->offload_info.usage == AUDIO_USAGE_MEDIA) ||
1721 (config->offload_info.usage == AUDIO_USAGE_GAME))) {
1722 audio_output_flags_t old_flags = *flags;
1723 *flags = (audio_output_flags_t)(AUDIO_OUTPUT_FLAG_DIRECT);
1724 ALOGD("Force Direct Flag .. old flags(0x%x)", old_flags);
1725 } else if (*flags == AUDIO_OUTPUT_FLAG_DIRECT &&
1726 (offload_disabled || stream != AUDIO_STREAM_MUSIC)) {
1727 ALOGD("Offloading is disabled or Stream is not music --> Force Remove Direct Flag");
1728 *flags = (audio_output_flags_t)(AUDIO_OUTPUT_FLAG_NONE);
1729 }
1730
1731 // check if direct output for pcm/track offload already exits
1732 bool direct_pcm_already_in_use = false;
1733 if (*flags == AUDIO_OUTPUT_FLAG_DIRECT) {
1734 for (size_t i = 0; i < mOutputs.size(); i++) {
1735 sp<SwAudioOutputDescriptor> desc = mOutputs.valueAt(i);
1736 if (desc->mFlags == AUDIO_OUTPUT_FLAG_DIRECT) {
1737 direct_pcm_already_in_use = true;
1738 ALOGD("Direct PCM already in use");
1739 break;
1740 }
1741 }
1742 // prevent direct pcm for non-music stream blindly if direct pcm already in use
1743 // for other music stream concurrency is handled after checking direct ouput usage
1744 // and checking client
1745 if (direct_pcm_already_in_use == true && stream != AUDIO_STREAM_MUSIC) {
1746 ALOGD("disabling offload for non music stream as direct pcm is already in use");
1747 *flags = (audio_output_flags_t)(AUDIO_OUTPUT_FLAG_NONE);
1748 }
1749 }
1750
1751 bool forced_deep = false;
1752 // only allow deep buffering for music stream type
1753 if (stream != AUDIO_STREAM_MUSIC) {
1754 *flags = (audio_output_flags_t)(*flags &~AUDIO_OUTPUT_FLAG_DEEP_BUFFER);
1755 } else if (/* stream == AUDIO_STREAM_MUSIC && */
1756 (*flags == AUDIO_OUTPUT_FLAG_NONE || *flags == AUDIO_OUTPUT_FLAG_DIRECT) &&
1757 property_get_bool("audio.deep_buffer.media", false /* default_value */) && !isInCall()) {
1758 forced_deep = true;
1759 }
1760
1761 if (stream == AUDIO_STREAM_TTS) {
1762 *flags = AUDIO_OUTPUT_FLAG_TTS;
1763 } else if (stream == AUDIO_STREAM_VOICE_CALL &&
1764 audio_is_linear_pcm(config->format)) {
1765 *flags = (audio_output_flags_t)(AUDIO_OUTPUT_FLAG_VOIP_RX |
1766 AUDIO_OUTPUT_FLAG_DIRECT);
1767 ALOGV("Set VoIP and Direct output flags for PCM format");
1768 } else if (device == AUDIO_DEVICE_OUT_TELEPHONY_TX &&
1769 stream == AUDIO_STREAM_MUSIC &&
1770 audio_is_linear_pcm(config->format) &&
1771 isInCall()) {
1772 *flags = (audio_output_flags_t)AUDIO_OUTPUT_FLAG_INCALL_MUSIC;
1773 }
1774
1775 sp<IOProfile> profile;
1776
1777 // skip direct output selection if the request can obviously be attached to a mixed output
1778 // and not explicitly requested
1779 if (((*flags & AUDIO_OUTPUT_FLAG_DIRECT) == 0) &&
1780 audio_is_linear_pcm(config->format) && config->sample_rate <= SAMPLE_RATE_HZ_MAX &&
1781 audio_channel_count_from_out_mask(config->channel_mask) <= 2) {
1782 goto non_direct_output;
1783 }
1784
1785 // Do not allow offloading if one non offloadable effect is enabled or MasterMono is enabled.
1786 // This prevents creating an offloaded track and tearing it down immediately after start
1787 // when audioflinger detects there is an active non offloadable effect.
1788 // FIXME: We should check the audio session here but we do not have it in this context.
1789 // This may prevent offloading in rare situations where effects are left active by apps
1790 // in the background.
1791 //
1792 // Supplementary annotation:
1793 // For sake of track offload introduced, we need a rollback for both compress offload
1794 // and track offload use cases.
1795 if ((*flags & (AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD|AUDIO_OUTPUT_FLAG_DIRECT)) &&
1796 (mEffects.isNonOffloadableEffectEnabled() || mMasterMono)) {
1797 ALOGD("non offloadable effect is enabled, try with non direct output");
1798 goto non_direct_output;
1799 }
1800
1801 profile = getProfileForDirectOutput(device,
1802 config->sample_rate,
1803 config->format,
1804 config->channel_mask,
1805 (audio_output_flags_t)*flags);
1806
1807 if (profile != 0) {
1808
1809 if (!(*flags & AUDIO_OUTPUT_FLAG_DIRECT) &&
1810 (profile->getFlags() & AUDIO_OUTPUT_FLAG_DIRECT)) {
1811 ALOGI("got Direct without requesting ... reject ");
1812 profile = NULL;
1813 goto non_direct_output;
1814 }
1815
1816 if ((*flags & AUDIO_OUTPUT_FLAG_MMAP_NOIRQ) == 0 || output != AUDIO_IO_HANDLE_NONE) {
1817 sp<SwAudioOutputDescriptor> outputDesc = NULL;
1818 // if multiple concurrent offload decode is supported
1819 // do no check for reuse and also don't close previous output if its offload
1820 // previous output will be closed during track destruction
1821 if (!(property_get_bool("vendor.audio.offload.multiple.enabled", false) &&
1822 ((*flags & AUDIO_OUTPUT_FLAG_DIRECT) != 0))) {
1823 for (size_t i = 0; i < mOutputs.size(); i++) {
1824 sp<SwAudioOutputDescriptor> desc = mOutputs.valueAt(i);
1825 if (!desc->isDuplicated() && (profile == desc->mProfile)) {
1826 outputDesc = desc;
1827 // reuse direct output if currently open by the same client
1828 // and configured with same parameters
1829 if ((config->sample_rate == desc->mSamplingRate) &&
1830 audio_formats_match(config->format, desc->mFormat) &&
1831 (config->channel_mask == desc->mChannelMask) &&
1832 (session == desc->mDirectClientSession)) {
1833 desc->mDirectOpenCount++;
1834 ALOGV("getOutputForDevice() reusing direct output %d for session %d",
1835 mOutputs.keyAt(i), session);
1836 return mOutputs.keyAt(i);
1837 }
1838 }
1839 }
1840 if (outputDesc != NULL) {
1841 if (*flags == AUDIO_OUTPUT_FLAG_DIRECT &&
1842 direct_pcm_already_in_use == true &&
1843 session != outputDesc->mDirectClientSession) {
1844 ALOGV("getOutput() do not reuse direct pcm output because current client (%d) "
1845 "is not the same as requesting client (%d) for different output conf",
1846 outputDesc->mDirectClientSession, session);
1847 goto non_direct_output;
1848 }
1849 closeOutput(outputDesc->mIoHandle);
1850 }
1851
1852 }
1853 if (!profile->canOpenNewIo()) {
1854 goto non_direct_output;
1855 }
1856
1857 outputDesc =
1858 new SwAudioOutputDescriptor(profile, mpClientInterface);
1859 DeviceVector outputDevices = mAvailableOutputDevices.getDevicesFromType(device);
1860 String8 address = outputDevices.size() > 0 ? outputDevices.itemAt(0)->mAddress
1861 : String8("");
1862 status = outputDesc->open(config, device, address, stream, *flags, &output);
1863
1864 // only accept an output with the requested parameters
1865 if (status != NO_ERROR ||
1866 (config->sample_rate != 0 && config->sample_rate != outputDesc->mSamplingRate) ||
1867 (config->format != AUDIO_FORMAT_DEFAULT &&
1868 !audio_formats_match(config->format, outputDesc->mFormat)) ||
1869 (config->channel_mask != 0 && config->channel_mask != outputDesc->mChannelMask)) {
1870 ALOGV("getOutputForDevice() failed opening direct output: output %d sample rate %d %d,"
1871 "format %d %d, channel mask %04x %04x", output, config->sample_rate,
1872 outputDesc->mSamplingRate, config->format, outputDesc->mFormat,
1873 config->channel_mask, outputDesc->mChannelMask);
1874 if (output != AUDIO_IO_HANDLE_NONE) {
1875 outputDesc->close();
1876 }
1877 // fall back to mixer output if possible when the direct output could not be open
1878 if (audio_is_linear_pcm(config->format) && config->sample_rate <= SAMPLE_RATE_HZ_MAX) {
1879 goto non_direct_output;
1880 }
1881 return AUDIO_IO_HANDLE_NONE;
1882 }
1883 outputDesc->mRefCount[stream] = 0;
1884 outputDesc->mStopTime[stream] = 0;
1885 outputDesc->mDirectOpenCount = 1;
1886 outputDesc->mDirectClientSession = session;
1887
1888 addOutput(output, outputDesc);
1889 mPreviousOutputs = mOutputs;
1890 ALOGV("getOutputForDevice() returns new direct output %d", output);
1891 mpClientInterface->onAudioPortListUpdate();
1892 return output;
1893 }
1894 }
1895
1896non_direct_output:
1897
1898 // A request for HW A/V sync cannot fallback to a mixed output because time
1899 // stamps are embedded in audio data
1900 if ((*flags & (AUDIO_OUTPUT_FLAG_HW_AV_SYNC | AUDIO_OUTPUT_FLAG_MMAP_NOIRQ)) != 0) {
1901 return AUDIO_IO_HANDLE_NONE;
1902 }
1903
1904 // ignoring channel mask due to downmix capability in mixer
1905
1906 // open a non direct output
1907
1908 // for non direct outputs, only PCM is supported
1909 if (audio_is_linear_pcm(config->format)) {
1910 // get which output is suitable for the specified stream. The actual
1911 // routing change will happen when startOutput() will be called
1912 SortedVector<audio_io_handle_t> outputs = getOutputsForDevice(device, mOutputs);
1913
1914 // at this stage we should ignore the DIRECT flag as no direct output could be found earlier
1915 *flags = (audio_output_flags_t)(*flags & ~AUDIO_OUTPUT_FLAG_DIRECT);
1916
1917 if (forced_deep) {
1918 *flags = (audio_output_flags_t)(AUDIO_OUTPUT_FLAG_DEEP_BUFFER);
1919 ALOGI("setting force DEEP buffer now ");
1920 } else if(*flags == AUDIO_OUTPUT_FLAG_NONE) {
1921 // no deep buffer playback is requested hence fallback to primary
1922 *flags = (audio_output_flags_t)(AUDIO_OUTPUT_FLAG_PRIMARY);
1923 ALOGI("FLAG None hence request for a primary output");
1924 }
1925
1926 output = selectOutput(outputs, *flags, config->format);
1927 }
1928
1929 ALOGW_IF((output == 0), "getOutputForDevice() could not find output for stream %d, "
1930 "sampling rate %d, format %#x, channels %#x, flags %#x",
1931 stream, config->sample_rate, config->format, config->channel_mask, *flags);
1932
1933 ALOGV("getOutputForDevice() returns output %d", output);
1934
1935 return output;
1936}
1937
1938status_t AudioPolicyManagerCustom::getInputForAttr(const audio_attributes_t *attr,
1939 audio_io_handle_t *input,
1940 audio_session_t session,
1941 uid_t uid,
1942 const audio_config_base_t *config,
1943 audio_input_flags_t flags,
1944 audio_port_handle_t *selectedDeviceId,
1945 input_type_t *inputType,
1946 audio_port_handle_t *portId)
1947{
1948 audio_source_t inputSource;
1949 inputSource = attr->source;
1950#ifdef VOICE_CONCURRENCY
1951
1952 char propValue[PROPERTY_VALUE_MAX];
1953 bool prop_rec_enabled=false, prop_voip_enabled = false;
1954
1955 if(property_get("vendor.voice.record.conc.disabled", propValue, NULL)) {
1956 prop_rec_enabled = atoi(propValue) || !strncmp("true", propValue, 4);
1957 }
1958
1959 if(property_get("vendor.voice.voip.conc.disabled", propValue, NULL)) {
1960 prop_voip_enabled = atoi(propValue) || !strncmp("true", propValue, 4);
1961 }
1962
1963 if (prop_rec_enabled && mvoice_call_state) {
1964 //check if voice call is active / running in background
1965 //some of VoIP apps(like SIP2SIP call) supports resume of VoIP call when call in progress
1966 //Need to block input request
1967 if((AUDIO_MODE_IN_CALL == mEngine->getPhoneState()) ||
1968 ((AUDIO_MODE_IN_CALL == mPrevPhoneState) &&
1969 (AUDIO_MODE_IN_COMMUNICATION == mEngine->getPhoneState())))
1970 {
1971 switch(inputSource) {
1972 case AUDIO_SOURCE_VOICE_UPLINK:
1973 case AUDIO_SOURCE_VOICE_DOWNLINK:
1974 case AUDIO_SOURCE_VOICE_CALL:
1975 ALOGD("voice_conc:Creating input during incall mode for inputSource: %d",
1976 inputSource);
1977 break;
1978
1979 case AUDIO_SOURCE_VOICE_COMMUNICATION:
1980 if(prop_voip_enabled) {
1981 ALOGD("voice_conc:BLOCK VoIP requst incall mode for inputSource: %d",
1982 inputSource);
1983 return NO_INIT;
1984 }
1985 break;
1986 default:
1987 ALOGD("voice_conc:BLOCK VoIP requst incall mode for inputSource: %d",
1988 inputSource);
1989 return NO_INIT;
1990 }
1991 }
1992 }//check for VoIP flag
1993 else if(prop_voip_enabled && mvoice_call_state) {
1994 //check if voice call is active / running in background
1995 //some of VoIP apps(like SIP2SIP call) supports resume of VoIP call when call in progress
1996 //Need to block input request
1997 if((AUDIO_MODE_IN_CALL == mEngine->getPhoneState()) ||
1998 ((AUDIO_MODE_IN_CALL == mPrevPhoneState) &&
1999 (AUDIO_MODE_IN_COMMUNICATION == mEngine->getPhoneState())))
2000 {
2001 if(inputSource == AUDIO_SOURCE_VOICE_COMMUNICATION) {
2002 ALOGD("BLOCKING VoIP request during incall mode for inputSource: %d ",inputSource);
2003 return NO_INIT;
2004 }
2005 }
2006 }
2007
2008#endif
2009
2010 return AudioPolicyManager::getInputForAttr(attr,
2011 input,
2012 session,
2013 uid,
2014 config,
2015 flags,
2016 selectedDeviceId,
2017 inputType,
2018 portId);
2019}
2020
2021uint32_t AudioPolicyManagerCustom::activeNonSoundTriggerInputsCountOnDevices(audio_devices_t devices) const
2022{
2023 uint32_t count = 0;
2024 for (size_t i = 0; i < mInputs.size(); i++) {
2025 const sp<AudioInputDescriptor> inputDescriptor = mInputs.valueAt(i);
2026 if (inputDescriptor->isActive() && !inputDescriptor->isSoundTrigger() &&
2027 ((devices == AUDIO_DEVICE_IN_DEFAULT) ||
2028 ((inputDescriptor->mDevice & devices & ~AUDIO_DEVICE_BIT_IN) != 0))) {
2029 count++;
2030 }
2031 }
2032 return count;
2033}
2034
2035status_t AudioPolicyManagerCustom::startInput(audio_io_handle_t input,
2036 audio_session_t session,
2037 bool silenced,
2038 concurrency_type__mask_t *concurrency)
2039{
2040
2041 ALOGV("startInput(input:%d, session:%d, silenced:%d, concurrency:%d)",
2042 input, session, silenced, *concurrency);
2043 *concurrency = API_INPUT_CONCURRENCY_NONE;
2044 ssize_t index = mInputs.indexOfKey(input);
2045 if (index < 0) {
2046 ALOGW("startInput() unknown input %d", input);
2047 return BAD_VALUE;
2048 }
2049 sp<AudioInputDescriptor> inputDesc = mInputs.valueAt(index);
2050
2051 sp<AudioSession> audioSession = inputDesc->getAudioSession(session);
2052 if (audioSession == 0) {
2053 ALOGW("startInput() unknown session %d on input %d", session, input);
2054 return BAD_VALUE;
2055 }
2056
2057// FIXME: disable concurrent capture until UI is ready
2058#if 0
2059 if (!isConcurentCaptureAllowed(inputDesc, audioSession)) {
2060 ALOGW("startInput(%d) failed: other input already started", input);
2061 return INVALID_OPERATION;
2062 }
2063
2064 if (isInCall()) {
2065 *concurrency |= API_INPUT_CONCURRENCY_CALL;
2066 }
2067
2068 if (mInputs.activeInputsCountOnDevices() != 0) {
2069 *concurrency |= API_INPUT_CONCURRENCY_CAPTURE;
2070 }
2071#else
2072 if (!is_virtual_input_device(inputDesc->mDevice)) {
2073 if (mCallTxPatch != 0 &&
2074 inputDesc->getModuleHandle() == mCallTxPatch->mPatch.sources[0].ext.device.hw_module) {
2075 ALOGW("startInput(%d) failed: call in progress", input);
2076 return INVALID_OPERATION;
2077 }
2078
2079 Vector< sp<AudioInputDescriptor> > activeInputs = mInputs.getActiveInputs();
2080
2081 // If a UID is idle and records silence and another not silenced recording starts
2082 // from another UID (idle or active) we stop the current idle UID recording in
2083 // favor of the new one - "There can be only one" TM
2084 if (!silenced) {
2085
2086 for (const auto& activeDesc : activeInputs) {
2087 if ((audioSession->flags() & AUDIO_INPUT_FLAG_MMAP_NOIRQ) != 0 &&
2088 activeDesc->getId() == inputDesc->getId()) {
2089 continue;
2090 }
2091
2092 AudioSessionCollection activeSessions = activeDesc->getAudioSessions(
2093 true /*activeOnly*/);
2094 sp<AudioSession> activeSession = activeSessions.valueAt(0);
2095 if (activeSession->isSilenced()) {
2096 audio_io_handle_t activeInput = activeDesc->mIoHandle;
2097 audio_session_t activeSessionId = activeSession->session();
2098 stopInput(activeInput, activeSessionId);
2099 releaseInput(activeInput, activeSessionId);
2100 ALOGV("startInput(%d) stopping silenced input %d", input, activeInput);
2101 activeInputs = mInputs.getActiveInputs();
2102 }
2103 }
2104 }
2105 for (const auto& activeDesc : activeInputs) {
2106 if ((audioSession->flags() & AUDIO_INPUT_FLAG_MMAP_NOIRQ) != 0 &&
2107 activeDesc->getId() == inputDesc->getId()) {
2108 continue;
2109 }
2110 // Don't allow sound triggers streams to preempt one another.
2111 if (inputDesc->isSoundTrigger() && activeDesc->isSoundTrigger()) {
2112 continue;
2113 }
2114
2115 audio_source_t activeSource = activeDesc->inputSource(true);
2116 if (audioSession->inputSource() == AUDIO_SOURCE_HOTWORD) {
2117 if (activeSource == AUDIO_SOURCE_HOTWORD) {
2118 if (activeDesc->hasPreemptedSession(session)) {
2119 ALOGW("startInput(%d) failed for HOTWORD: "
2120 "other input %d already started for HOTWORD",
2121 input, activeDesc->mIoHandle);
2122 return INVALID_OPERATION;
2123 }
2124 } else {
2125 ALOGV("startInput(%d) failed for HOTWORD: other input %d already started",
2126 input, activeDesc->mIoHandle);
2127 return INVALID_OPERATION;
2128 }
2129 } else {
2130 if (activeSource != AUDIO_SOURCE_HOTWORD) {
2131 ALOGW("startInput(%d) failed: other input %d already started",
2132 input, activeDesc->mIoHandle);
2133 return INVALID_OPERATION;
2134 }
2135 }
2136 }
2137
2138 // We only need to check if the sound trigger session supports concurrent capture if the
2139 // input is also a sound trigger input. Otherwise, we should preempt any hotword stream
2140 // that's running.
2141 const bool allowConcurrentWithSoundTrigger =
2142 inputDesc->isSoundTrigger() ? soundTriggerSupportsConcurrentCapture() : false;
2143
2144 // if capture is allowed, preempt currently active HOTWORD captures
2145 for (const auto& activeDesc : activeInputs) {
2146 if (allowConcurrentWithSoundTrigger && activeDesc->isSoundTrigger()) {
2147 continue;
2148 }
2149
2150 audio_source_t activeSource = activeDesc->inputSource(true);
2151 if (activeSource == AUDIO_SOURCE_HOTWORD) {
2152 AudioSessionCollection activeSessions =
2153 activeDesc->getAudioSessions(true /*activeOnly*/);
2154 audio_session_t activeSession = activeSessions.keyAt(0);
2155 audio_io_handle_t activeHandle = activeDesc->mIoHandle;
2156 SortedVector<audio_session_t> sessions = activeDesc->getPreemptedSessions();
2157 sessions.add(activeSession);
2158 inputDesc->setPreemptedSessions(sessions);
2159 stopInput(activeHandle, activeSession);
2160 releaseInput(activeHandle, activeSession);
2161 ALOGV("startInput(%d) for HOTWORD preempting HOTWORD input %d",
2162 input, activeDesc->mIoHandle);
2163 }
2164 }
2165 }
2166#endif
2167
2168#ifdef RECORD_PLAY_CONCURRENCY
2169 mIsInputRequestOnProgress = true;
2170
2171 char getPropValue[PROPERTY_VALUE_MAX];
2172 bool prop_rec_play_enabled = false;
2173
2174 if (property_get("vendor.audio.rec.playback.conc.disabled", getPropValue, NULL)) {
2175 prop_rec_play_enabled = atoi(getPropValue) || !strncmp("true", getPropValue, 4);
2176 }
2177
2178 if ((prop_rec_play_enabled) && (mInputs.activeInputsCountOnDevices() == 0)){
2179 // send update to HAL on record playback concurrency
2180 AudioParameter param = AudioParameter();
2181 param.add(String8("rec_play_conc_on"), String8("true"));
2182 ALOGD("startInput() setParameters rec_play_conc is setting to ON ");
2183 mpClientInterface->setParameters(0, param.toString());
2184
2185 // Call invalidate to reset all opened non ULL audio tracks
2186 // Move tracks associated to this strategy from previous output to new output
2187 for (int i = AUDIO_STREAM_SYSTEM; i < AUDIO_STREAM_FOR_POLICY_CNT; i++) {
2188 // Do not call invalidate for ENFORCED_AUDIBLE (otherwise pops are seen for camcorder)
2189 if (i != AUDIO_STREAM_ENFORCED_AUDIBLE) {
2190 ALOGD("Invalidate on releaseInput for stream :: %d ", i);
2191 //FIXME see fixme on name change
2192 mpClientInterface->invalidateStream((audio_stream_type_t)i);
2193 }
2194 }
2195 // close compress tracks
2196 for (size_t i = 0; i < mOutputs.size(); i++) {
2197 sp<SwAudioOutputDescriptor> outputDesc = mOutputs.valueAt(i);
2198 if ((outputDesc == NULL) || (outputDesc->mProfile == NULL)) {
2199 ALOGD("ouput desc / profile is NULL");
2200 continue;
2201 }
2202 if (outputDesc->mProfile->getFlags()
2203 & AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD) {
2204 // close compress sessions
2205 ALOGD("calling closeOutput on record conc for COMPRESS output");
2206 closeOutput(mOutputs.keyAt(i));
2207 }
2208 }
2209 }
2210#endif
2211
2212 // increment activity count before calling getNewInputDevice() below as only active sessions
2213 // are considered for device selection
2214 audioSession->changeActiveCount(1);
2215
2216 // Routing?
2217 mInputRoutes.incRouteActivity(session);
2218
2219 if (audioSession->activeCount() == 1 || mInputRoutes.getAndClearRouteChanged(session)) {
2220 // indicate active capture to sound trigger service if starting capture from a mic on
2221 // primary HW module
2222 audio_devices_t device = getNewInputDevice(inputDesc);
2223 setInputDevice(input, device, true /* force */);
2224 status_t status = inputDesc->start();
2225 if (status != NO_ERROR) {
2226 mInputRoutes.decRouteActivity(session);
2227 audioSession->changeActiveCount(-1);
2228 return status;
2229 }
2230
2231 if (inputDesc->getAudioSessionCount(true/*activeOnly*/) == 1) {
2232 // if input maps to a dynamic policy with an activity listener, notify of state change
2233 if ((inputDesc->mPolicyMix != NULL)
2234 && ((inputDesc->mPolicyMix->mCbFlags & AudioMix::kCbFlagNotifyActivity) != 0)) {
2235 mpClientInterface->onDynamicPolicyMixStateUpdate(inputDesc->mPolicyMix->mDeviceAddress,
2236 MIX_STATE_MIXING);
2237 }
2238
2239 audio_devices_t primaryInputDevices = availablePrimaryInputDevices();
2240 if ((device & primaryInputDevices & ~AUDIO_DEVICE_BIT_IN) != 0) {
2241 if (property_get_bool("persist.vendor.audio.va_concurrency_enabled", false)) {
2242 if (activeNonSoundTriggerInputsCountOnDevices(primaryInputDevices) == 1)
2243 SoundTrigger::setCaptureState(true);
2244 } else if (mInputs.activeInputsCountOnDevices(primaryInputDevices) == 1)
2245 SoundTrigger::setCaptureState(true);
2246 }
2247
2248 // automatically enable the remote submix output when input is started if not
2249 // used by a policy mix of type MIX_TYPE_RECORDERS
2250 // For remote submix (a virtual device), we open only one input per capture request.
2251 if (audio_is_remote_submix_device(inputDesc->mDevice)) {
2252 String8 address = String8("");
2253 if (inputDesc->mPolicyMix == NULL) {
2254 address = String8("0");
2255 } else if (inputDesc->mPolicyMix->mMixType == MIX_TYPE_PLAYERS) {
2256 address = inputDesc->mPolicyMix->mDeviceAddress;
2257 }
2258 if (address != "") {
2259 setDeviceConnectionStateInt(AUDIO_DEVICE_OUT_REMOTE_SUBMIX,
2260 AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
2261 address, "remote-submix");
2262 }
2263 }
2264 }
2265 }
2266
2267 ALOGV("AudioPolicyManager::startInput() input source = %d", audioSession->inputSource());
2268#ifdef RECORD_PLAY_CONCURRENCY
2269 mIsInputRequestOnProgress = false;
2270#endif
2271 return NO_ERROR;
2272}
2273
2274status_t AudioPolicyManagerCustom::stopInput(audio_io_handle_t input,
2275 audio_session_t session)
2276{
2277 status_t status;
2278 status = AudioPolicyManager::stopInput(input, session);
2279 if (property_get_bool("persist.vendor.audio.va_concurrency_enabled", false)) {
2280 ssize_t index = mInputs.indexOfKey(input);
2281 sp<AudioInputDescriptor> inputDesc = mInputs.valueAt(index);
2282 audio_devices_t device = inputDesc->mDevice;
2283 audio_devices_t primaryInputDevices = availablePrimaryInputDevices();
2284 if (((device & primaryInputDevices & ~AUDIO_DEVICE_BIT_IN) != 0) &&
2285 activeNonSoundTriggerInputsCountOnDevices(primaryInputDevices) == 0) {
2286 SoundTrigger::setCaptureState(false);
2287 }
2288 }
2289#ifdef RECORD_PLAY_CONCURRENCY
2290 char propValue[PROPERTY_VALUE_MAX];
2291 bool prop_rec_play_enabled = false;
2292
2293 if (property_get("vendor.audio.rec.playback.conc.disabled", propValue, NULL)) {
2294 prop_rec_play_enabled = atoi(propValue) || !strncmp("true", propValue, 4);
2295 }
2296
2297 if ((prop_rec_play_enabled) && (mInputs.activeInputsCountOnDevices() == 0)) {
2298
2299 //send update to HAL on record playback concurrency
2300 AudioParameter param = AudioParameter();
2301 param.add(String8("rec_play_conc_on"), String8("false"));
2302 ALOGD("stopInput() setParameters rec_play_conc is setting to OFF ");
2303 mpClientInterface->setParameters(0, param.toString());
2304
2305 //call invalidate tracks so that any open streams can fall back to deep buffer/compress path from ULL
2306 for (int i = AUDIO_STREAM_SYSTEM; i < (int)AUDIO_STREAM_CNT; i++) {
2307 //Do not call invalidate for ENFORCED_AUDIBLE (otherwise pops are seen for camcorder stop tone)
2308 if ((i != AUDIO_STREAM_ENFORCED_AUDIBLE) && (i != AUDIO_STREAM_PATCH)) {
2309 ALOGD(" Invalidate on stopInput for stream :: %d ", i);
2310 //FIXME see fixme on name change
2311 mpClientInterface->invalidateStream((audio_stream_type_t)i);
2312 }
2313 }
2314 }
2315#endif
2316 return status;
2317}
2318
2319AudioPolicyManagerCustom::AudioPolicyManagerCustom(AudioPolicyClientInterface *clientInterface)
2320 : AudioPolicyManager(clientInterface),
2321 mHdmiAudioDisabled(false),
2322 mHdmiAudioEvent(false),
2323#ifndef FM_POWER_OPT
2324 mPrevPhoneState(0)
2325#else
2326 mPrevPhoneState(0),
2327 mPrevFMVolumeDb(0.0f),
2328 mFMIsActive(false)
2329#endif
2330{
2331
2332#ifdef USE_XML_AUDIO_POLICY_CONF
2333 ALOGD("USE_XML_AUDIO_POLICY_CONF is TRUE");
2334#else
2335 ALOGD("USE_XML_AUDIO_POLICY_CONF is FALSE");
2336#endif
2337
2338#ifdef RECORD_PLAY_CONCURRENCY
2339 mIsInputRequestOnProgress = false;
2340#endif
2341
2342
2343#ifdef VOICE_CONCURRENCY
2344 mFallBackflag = getFallBackPath();
2345#endif
2346}
2347}