Merge "hal: fix no audio in qchat call with speaker as default device"
diff --git a/hal/audio_extn/audio_extn.h b/hal/audio_extn/audio_extn.h
index e17aa6b..72f8642 100644
--- a/hal/audio_extn/audio_extn.h
+++ b/hal/audio_extn/audio_extn.h
@@ -165,4 +165,10 @@
int audio_extn_dolby_set_DMID(struct audio_device *adev);
#endif
+#ifndef HFP_ENABLED
+#define audio_extn_hfp_is_active(adev) (0)
+#else
+bool audio_extn_hfp_is_active(struct audio_device *adev);
+#endif
+
#endif /* AUDIO_EXTN_H */
diff --git a/hal/audio_extn/hfp.c b/hal/audio_extn/hfp.c
index 4eb9d37..2d6e1e0 100644
--- a/hal/audio_extn/hfp.c
+++ b/hal/audio_extn/hfp.c
@@ -217,10 +217,22 @@
return ret;
}
+bool audio_extn_hfp_is_active(struct audio_device *adev)
+{
+ struct audio_usecase *hfp_usecase = NULL;
+ hfp_usecase = get_usecase_from_list(adev, USECASE_AUDIO_HFP_SCO);
+
+ if (hfp_usecase != NULL)
+ return true;
+ else
+ return false;
+}
+
void audio_extn_hfp_set_parameters(struct audio_device *adev, struct str_parms *parms)
{
int ret;
int rate;
+ int val;
char value[32]={0};
ret = str_parms_get_str(parms, AUDIO_PARAMETER_HFP_ENABLE, value,
@@ -247,5 +259,16 @@
else
ALOGE("Unsupported rate..");
}
+
+ if(hfpmod.is_hfp_running) {
+ memset(value, 0, sizeof(value));
+ ret = str_parms_get_str(parms, AUDIO_PARAMETER_STREAM_ROUTING,
+ value, sizeof(value));
+ if (ret >= 0) {
+ val = atoi(value);
+ if(val > 0)
+ select_devices(adev, hfpmod.ucid);
+ }
+ }
}
#endif /*HFP_ENABLED*/
diff --git a/hal/audio_hw.c b/hal/audio_hw.c
index ff33b7d..61e291d 100644
--- a/hal/audio_hw.c
+++ b/hal/audio_hw.c
@@ -370,7 +370,7 @@
list_for_each(node, &adev->usecase_list) {
usecase = node_to_item(node, struct audio_usecase, list);
- if (usecase->type == PCM_PLAYBACK &&
+ if (usecase->type != PCM_CAPTURE &&
usecase != uc_info &&
usecase->out_snd_device != snd_device &&
usecase->devices & AUDIO_DEVICE_OUT_ALL_CODEC_BACKEND) {
@@ -414,8 +414,6 @@
enable_audio_route(adev, usecase, false);
}
}
-
- audio_route_update_mixer(adev->audio_route);
}
}
@@ -443,7 +441,7 @@
list_for_each(node, &adev->usecase_list) {
usecase = node_to_item(node, struct audio_usecase, list);
- if (usecase->type == PCM_CAPTURE &&
+ if (usecase->type != PCM_PLAYBACK &&
usecase != uc_info &&
usecase->in_snd_device != snd_device) {
ALOGV("%s: Usecase (%s) is active on (%s) - disabling ..",
@@ -463,6 +461,12 @@
usecase = node_to_item(node, struct audio_usecase, list);
if (switch_device[usecase->id]) {
disable_snd_device(adev, usecase->in_snd_device, false);
+ }
+ }
+
+ list_for_each(node, &adev->usecase_list) {
+ usecase = node_to_item(node, struct audio_usecase, list);
+ if (switch_device[usecase->id]) {
enable_snd_device(adev, snd_device, false);
}
}
@@ -480,57 +484,9 @@
enable_audio_route(adev, usecase, false);
}
}
-
- audio_route_update_mixer(adev->audio_route);
}
}
-static int disable_all_usecases_of_type(struct audio_device *adev,
- usecase_type_t usecase_type,
- bool update_mixer)
-{
- struct audio_usecase *usecase;
- struct listnode *node;
- int ret = 0;
-
- list_for_each(node, &adev->usecase_list) {
- usecase = node_to_item(node, struct audio_usecase, list);
- if (usecase->type == usecase_type) {
- ALOGV("%s: usecase id %d", __func__, usecase->id);
- ret = disable_audio_route(adev, usecase, update_mixer);
- if (ret) {
- ALOGE("%s: Failed to disable usecase id %d",
- __func__, usecase->id);
- }
- }
- }
-
- return ret;
-}
-
-static int enable_all_usecases_of_type(struct audio_device *adev,
- usecase_type_t usecase_type,
- bool update_mixer)
-{
- struct audio_usecase *usecase;
- struct listnode *node;
- int ret = 0;
-
- list_for_each(node, &adev->usecase_list) {
- usecase = node_to_item(node, struct audio_usecase, list);
- if (usecase->type == usecase_type) {
- ALOGV("%s: usecase id %d", __func__, usecase->id);
- ret = enable_audio_route(adev, usecase, update_mixer);
- if (ret) {
- ALOGE("%s: Failed to enable usecase id %d",
- __func__, usecase->id);
- }
- }
- }
-
- return ret;
-}
-
/* must be called with hw device mutex locked */
static int read_hdmi_channel_masks(struct stream_out *out)
{
@@ -559,6 +515,21 @@
return ret;
}
+static void update_devices_for_all_voice_usecases(struct audio_device *adev)
+{
+ struct listnode *node;
+ struct audio_usecase *usecase;
+
+ list_for_each(node, &adev->usecase_list) {
+ usecase = node_to_item(node, struct audio_usecase, list);
+ if (usecase->type == VOICE_CALL) {
+ ALOGV("%s: updating device for usecase:%s", __func__,
+ use_case_table[usecase->id]);
+ select_devices(adev, usecase->id);
+ }
+ }
+}
+
static audio_usecase_t get_voice_usecase_id_from_list(struct audio_device *adev)
{
struct audio_usecase *usecase;
@@ -595,6 +566,7 @@
struct audio_usecase *usecase = NULL;
struct audio_usecase *vc_usecase = NULL;
struct audio_usecase *voip_usecase = NULL;
+ struct audio_usecase *hfp_usecase = NULL;
struct listnode *node;
int status = 0;
@@ -633,6 +605,12 @@
in_snd_device = voip_usecase->in_snd_device;
out_snd_device = voip_usecase->out_snd_device;
}
+ } else if (audio_extn_hfp_is_active(adev)) {
+ hfp_usecase = get_usecase_from_list(adev, USECASE_AUDIO_HFP_SCO);
+ if (hfp_usecase->devices & AUDIO_DEVICE_OUT_ALL_CODEC_BACKEND) {
+ in_snd_device = hfp_usecase->in_snd_device;
+ out_snd_device = hfp_usecase->out_snd_device;
+ }
}
if (usecase->type == PCM_PLAYBACK) {
usecase->devices = usecase->stream.out->devices;
@@ -678,7 +656,6 @@
*/
if (usecase->type == VOICE_CALL || usecase->type == VOIP_CALL) {
status = platform_switch_voice_call_device_pre(adev->platform);
- disable_all_usecases_of_type(adev, VOICE_CALL, true);
}
/* Disable current sound devices */
@@ -714,10 +691,7 @@
usecase->in_snd_device = in_snd_device;
usecase->out_snd_device = out_snd_device;
- if (usecase->type == VOICE_CALL || usecase->type == VOIP_CALL)
- enable_all_usecases_of_type(adev, usecase->type, true);
- else
- enable_audio_route(adev, usecase, true);
+ enable_audio_route(adev, usecase, true);
/* Applicable only on the targets that has external modem.
* Enable device command should be sent to modem only after
@@ -1411,7 +1385,7 @@
} else if ((adev->mode == AUDIO_MODE_IN_CALL) &&
voice_is_in_call(adev) &&
(out == adev->primary_output)) {
- ret = select_devices(adev, get_voice_usecase_id_from_list(adev));
+ update_devices_for_all_voice_usecases(adev);
}
}
diff --git a/hal/msm8974/platform.c b/hal/msm8974/platform.c
index f32ec94..807ede4 100644
--- a/hal/msm8974/platform.c
+++ b/hal/msm8974/platform.c
@@ -871,6 +871,36 @@
goto exit;
}
+ if (popcount(devices) == 2) {
+ if (devices == (AUDIO_DEVICE_OUT_WIRED_HEADPHONE |
+ AUDIO_DEVICE_OUT_SPEAKER)) {
+ snd_device = SND_DEVICE_OUT_SPEAKER_AND_HEADPHONES;
+ } else if (devices == (AUDIO_DEVICE_OUT_WIRED_HEADSET |
+ AUDIO_DEVICE_OUT_SPEAKER)) {
+ if (audio_extn_get_anc_enabled())
+ snd_device = SND_DEVICE_OUT_SPEAKER_AND_ANC_HEADSET;
+ else
+ snd_device = SND_DEVICE_OUT_SPEAKER_AND_HEADPHONES;
+ } else if (devices == (AUDIO_DEVICE_OUT_AUX_DIGITAL |
+ AUDIO_DEVICE_OUT_SPEAKER)) {
+ snd_device = SND_DEVICE_OUT_SPEAKER_AND_HDMI;
+ } else if (devices == (AUDIO_DEVICE_OUT_ANLG_DOCK_HEADSET |
+ AUDIO_DEVICE_OUT_SPEAKER)) {
+ snd_device = SND_DEVICE_OUT_SPEAKER_AND_USB_HEADSET;
+ } else {
+ ALOGE("%s: Invalid combo device(%#x)", __func__, devices);
+ goto exit;
+ }
+ if (snd_device != SND_DEVICE_NONE) {
+ goto exit;
+ }
+ }
+
+ if (popcount(devices) != 1) {
+ ALOGE("%s: Invalid output devices(%#x)", __func__, devices);
+ goto exit;
+ }
+
if ((mode == AUDIO_MODE_IN_CALL) ||
voice_extn_compress_voip_is_active(adev)) {
if (devices & AUDIO_DEVICE_OUT_WIRED_HEADPHONE ||
@@ -922,36 +952,6 @@
}
}
- if (popcount(devices) == 2) {
- if (devices == (AUDIO_DEVICE_OUT_WIRED_HEADPHONE |
- AUDIO_DEVICE_OUT_SPEAKER)) {
- snd_device = SND_DEVICE_OUT_SPEAKER_AND_HEADPHONES;
- } else if (devices == (AUDIO_DEVICE_OUT_WIRED_HEADSET |
- AUDIO_DEVICE_OUT_SPEAKER)) {
- if (audio_extn_get_anc_enabled())
- snd_device = SND_DEVICE_OUT_SPEAKER_AND_ANC_HEADSET;
- else
- snd_device = SND_DEVICE_OUT_SPEAKER_AND_HEADPHONES;
- } else if (devices == (AUDIO_DEVICE_OUT_AUX_DIGITAL |
- AUDIO_DEVICE_OUT_SPEAKER)) {
- snd_device = SND_DEVICE_OUT_SPEAKER_AND_HDMI;
- } else if (devices == (AUDIO_DEVICE_OUT_ANLG_DOCK_HEADSET |
- AUDIO_DEVICE_OUT_SPEAKER)) {
- snd_device = SND_DEVICE_OUT_SPEAKER_AND_USB_HEADSET;
- } else {
- ALOGE("%s: Invalid combo device(%#x)", __func__, devices);
- goto exit;
- }
- if (snd_device != SND_DEVICE_NONE) {
- goto exit;
- }
- }
-
- if (popcount(devices) != 1) {
- ALOGE("%s: Invalid output devices(%#x)", __func__, devices);
- goto exit;
- }
-
if (devices & AUDIO_DEVICE_OUT_WIRED_HEADPHONE ||
devices & AUDIO_DEVICE_OUT_WIRED_HEADSET) {
if (devices & AUDIO_DEVICE_OUT_WIRED_HEADSET
diff --git a/hal_mpq/audio_stream_out.c b/hal_mpq/audio_stream_out.c
index 7ef3255..c475a1e 100644
--- a/hal_mpq/audio_stream_out.c
+++ b/hal_mpq/audio_stream_out.c
@@ -2139,6 +2139,7 @@
/* TODO:disnable this if ms12 */
if (ret >= 0 && ret < (ssize_t)bytes) {
+ handle->cmd_pending = true;
send_offload_cmd_l(out, OFFLOAD_CMD_WAIT_FOR_BUFFER);
}
return ret;
diff --git a/policy_hal/AudioPolicyManager.cpp b/policy_hal/AudioPolicyManager.cpp
index d44a251..f64bbfe 100644
--- a/policy_hal/AudioPolicyManager.cpp
+++ b/policy_hal/AudioPolicyManager.cpp
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2013, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2013-2014, The Linux Foundation. All rights reserved.
* Not a contribution.
*
* Copyright (C) 2009 The Android Open Source Project
@@ -590,7 +590,7 @@
case STRATEGY_MEDIA: {
uint32_t device2 = AUDIO_DEVICE_NONE;
- if (isInCall()) {
+ if (isInCall() && (device == AUDIO_DEVICE_NONE)) {
// when in call, get the device for Phone strategy
device = getDeviceForStrategy(STRATEGY_PHONE, false /*fromCache*/);
break;