common: Reimplement mode change and input stream routing.
This commit is contained in:
parent
fc250744f4
commit
c93ea363b2
2 changed files with 129 additions and 43 deletions
|
|
@ -1221,6 +1221,17 @@ fail:
|
|||
return NULL;
|
||||
}
|
||||
|
||||
static const char *audio_mode_to_string(audio_mode_t mode) {
|
||||
switch (mode) {
|
||||
case AUDIO_MODE_RINGTONE: return "AUDIO_MODE_RINGTONE";
|
||||
case AUDIO_MODE_IN_CALL: return "AUDIO_MODE_IN_CALL";
|
||||
case AUDIO_MODE_IN_COMMUNICATION: return "AUDIO_MODE_IN_COMMUNICATION";
|
||||
default: break;
|
||||
}
|
||||
|
||||
return "AUDIO_MODE_NORMAL";
|
||||
}
|
||||
|
||||
static void set_active_input(pa_droid_hw_module *hw_module, pa_droid_stream *stream) {
|
||||
pa_assert(hw_module);
|
||||
|
||||
|
|
@ -1632,44 +1643,50 @@ static int droid_output_stream_set_route(pa_droid_stream *s, audio_devices_t dev
|
|||
return ret;
|
||||
}
|
||||
|
||||
static int input_stream_set_route(pa_droid_stream *s, audio_devices_t device) {
|
||||
static int input_stream_set_route(pa_droid_hw_module *hw_module) {
|
||||
pa_droid_stream *s;
|
||||
pa_droid_input_stream *input;
|
||||
audio_source_t source = (uint32_t) -1;
|
||||
char *parameters;
|
||||
audio_devices_t device;
|
||||
audio_source_t source;
|
||||
char *parameters = NULL;
|
||||
int ret = 0;
|
||||
|
||||
pa_assert(s);
|
||||
pa_assert(s->input);
|
||||
pa_assert(s->input->stream);
|
||||
pa_assert(hw_module);
|
||||
|
||||
/* No active input, no need for set parameters */
|
||||
if (!(s = hw_module->state.active_input))
|
||||
goto done;
|
||||
|
||||
input = s->input;
|
||||
|
||||
/* Input stream closed, no need for set parameters */
|
||||
if (!input->stream)
|
||||
goto done;
|
||||
|
||||
device = hw_module->state.input_device;
|
||||
source = hw_module->state.audio_source;
|
||||
#ifdef DROID_DEVICE_I9305
|
||||
device &= ~AUDIO_DEVICE_BIT_IN;
|
||||
#endif
|
||||
|
||||
if (pa_input_device_default_audio_source(device, &source)) {
|
||||
if (pa_droid_quirk(s->module, QUIRK_INPUT_ATOI))
|
||||
parameters = pa_sprintf_malloc("%s=%d;%s=%u", AUDIO_PARAMETER_STREAM_ROUTING, (int32_t) device,
|
||||
AUDIO_PARAMETER_STREAM_INPUT_SOURCE, source);
|
||||
else
|
||||
parameters = pa_sprintf_malloc("%s=%u;%s=%u", AUDIO_PARAMETER_STREAM_ROUTING, device,
|
||||
AUDIO_PARAMETER_STREAM_INPUT_SOURCE, source);
|
||||
} else
|
||||
parameters = pa_sprintf_malloc("%s=%u", AUDIO_PARAMETER_STREAM_ROUTING, device);
|
||||
if (pa_droid_quirk(hw_module, QUIRK_INPUT_ATOI))
|
||||
parameters = pa_sprintf_malloc("%s=%d;%s=%u", AUDIO_PARAMETER_STREAM_ROUTING, (int32_t) device,
|
||||
AUDIO_PARAMETER_STREAM_INPUT_SOURCE, source);
|
||||
else
|
||||
parameters = pa_sprintf_malloc("%s=%u;%s=%u", AUDIO_PARAMETER_STREAM_ROUTING, device,
|
||||
AUDIO_PARAMETER_STREAM_INPUT_SOURCE, source);
|
||||
|
||||
pa_log_debug("input stream %p set_parameters(%s) %#010x ; %#010x",
|
||||
(void *) s, parameters, device, source);
|
||||
(void *) input, parameters, device, source);
|
||||
|
||||
|
||||
if (pa_droid_quirk(s->module, QUIRK_SET_PARAMETERS)) {
|
||||
pa_mutex_lock(s->module->hw_mutex);
|
||||
ret = s->module->device->set_parameters(s->module->device, parameters);
|
||||
pa_mutex_unlock(s->module->hw_mutex);
|
||||
if (pa_droid_quirk(hw_module, QUIRK_SET_PARAMETERS)) {
|
||||
pa_mutex_lock(hw_module->hw_mutex);
|
||||
ret = hw_module->device->set_parameters(hw_module->device, parameters);
|
||||
pa_mutex_unlock(hw_module->hw_mutex);
|
||||
} else {
|
||||
pa_mutex_lock(s->module->input_mutex);
|
||||
pa_mutex_lock(hw_module->input_mutex);
|
||||
ret = input->stream->common.set_parameters(&input->stream->common, parameters);
|
||||
pa_mutex_unlock(s->module->input_mutex);
|
||||
pa_mutex_unlock(hw_module->input_mutex);
|
||||
}
|
||||
|
||||
if (ret < 0) {
|
||||
|
|
@ -1677,27 +1694,11 @@ static int input_stream_set_route(pa_droid_stream *s, audio_devices_t device) {
|
|||
pa_log_warn("input set_parameters(%s) not allowed while stream is active", parameters);
|
||||
else
|
||||
pa_log_warn("input set_parameters(%s) failed", parameters);
|
||||
} else
|
||||
input->device = device;
|
||||
}
|
||||
|
||||
pa_xfree(parameters);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int droid_input_stream_set_route(pa_droid_stream *s, audio_devices_t device) {
|
||||
int ret = 0;
|
||||
|
||||
pa_assert(s);
|
||||
pa_assert(s->input);
|
||||
|
||||
if (s->input->stream) {
|
||||
input_stream_set_route(s, device);
|
||||
} else {
|
||||
s->input->device = device;
|
||||
pa_log_debug("input stream (inactive) %p store route %#010x", (void *) s, device);
|
||||
}
|
||||
|
||||
done:
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
|
@ -1706,8 +1707,10 @@ int pa_droid_stream_set_route(pa_droid_stream *s, audio_devices_t device) {
|
|||
|
||||
if (s->output)
|
||||
return droid_output_stream_set_route(s, device);
|
||||
else
|
||||
return droid_input_stream_set_route(s, device);
|
||||
else {
|
||||
pa_droid_hw_set_input_device(s->module, device);
|
||||
return input_stream_set_route(s->module);
|
||||
}
|
||||
}
|
||||
|
||||
int pa_droid_stream_set_parameters(pa_droid_stream *s, const char *parameters) {
|
||||
|
|
@ -1897,6 +1900,86 @@ void pa_droid_hw_mic_set_mute(pa_droid_hw_module *hw_module, bool muted) {
|
|||
pa_droid_hw_module_unlock(hw_module);
|
||||
}
|
||||
|
||||
bool pa_droid_hw_set_mode(pa_droid_hw_module *hw_module, audio_mode_t mode) {
|
||||
bool ret = true;
|
||||
|
||||
pa_assert(hw_module);
|
||||
pa_assert(hw_module->device);
|
||||
|
||||
pa_log_info("Set mode to %s.", audio_mode_to_string(mode));
|
||||
|
||||
pa_droid_hw_module_lock(hw_module);
|
||||
if (hw_module->device->set_mode(hw_module->device, mode) < 0) {
|
||||
ret = false;
|
||||
pa_log_warn("Failed to set mode.");
|
||||
} else {
|
||||
hw_module->state.mode = mode;
|
||||
}
|
||||
pa_droid_hw_module_unlock(hw_module);
|
||||
|
||||
/* Update possible audio source. */
|
||||
pa_droid_hw_set_input_device(hw_module, hw_module->state.input_device);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
bool pa_droid_hw_set_input_device(pa_droid_hw_module *hw_module,
|
||||
audio_devices_t device) {
|
||||
audio_source_t audio_source = AUDIO_SOURCE_DEFAULT;
|
||||
audio_source_t audio_source_override = AUDIO_SOURCE_DEFAULT;
|
||||
bool device_changed = false;
|
||||
bool source_changed = false;
|
||||
const char *audio_source_name;
|
||||
|
||||
pa_assert(hw_module);
|
||||
|
||||
if (hw_module->state.input_device != device) {
|
||||
pa_log_debug("Set global input to %#010x", device);
|
||||
hw_module->state.input_device = device;
|
||||
device_changed = true;
|
||||
}
|
||||
|
||||
pa_input_device_default_audio_source(hw_module->state.input_device, &audio_source);
|
||||
|
||||
/* Override audio source based on mode. */
|
||||
switch (hw_module->state.mode) {
|
||||
case AUDIO_MODE_IN_CALL:
|
||||
audio_source_override = AUDIO_SOURCE_VOICE_CALL;
|
||||
break;
|
||||
case AUDIO_MODE_IN_COMMUNICATION:
|
||||
audio_source_override = AUDIO_SOURCE_VOICE_COMMUNICATION;
|
||||
break;
|
||||
default:
|
||||
audio_source_override = audio_source;
|
||||
break;
|
||||
}
|
||||
|
||||
if (audio_source != audio_source_override) {
|
||||
const char *from, *to;
|
||||
pa_droid_audio_source_name(audio_source, &from);
|
||||
pa_droid_audio_source_name(audio_source_override, &to);
|
||||
pa_log_info("Audio mode %s, overriding audio source %s with %s",
|
||||
audio_mode_to_string(hw_module->state.mode),
|
||||
from ? from : "<unknown>",
|
||||
to ? to : "<unknown>");
|
||||
audio_source = audio_source_override;
|
||||
}
|
||||
|
||||
if (audio_source != hw_module->state.audio_source) {
|
||||
pa_log_debug("set global audio source to %s (%#010x)",
|
||||
pa_droid_audio_source_name(audio_source, &audio_source_name)
|
||||
? audio_source_name : "<unknown>",
|
||||
audio_source);
|
||||
hw_module->state.audio_source = audio_source;
|
||||
source_changed = true;
|
||||
}
|
||||
|
||||
if (hw_module->state.active_input && (device_changed || source_changed))
|
||||
input_stream_set_route(hw_module);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
const pa_sample_spec *pa_droid_stream_sample_spec(pa_droid_stream *stream) {
|
||||
pa_assert(stream);
|
||||
pa_assert(stream->output || stream->input);
|
||||
|
|
|
|||
|
|
@ -246,6 +246,7 @@ static inline bool pa_droid_quirk(pa_droid_hw_module *hw, enum pa_droid_quirk_ty
|
|||
return hw->quirks && hw->quirks->enabled[quirk];
|
||||
}
|
||||
|
||||
bool pa_droid_hw_set_mode(pa_droid_hw_module *hw_module, audio_mode_t mode);
|
||||
bool pa_droid_hw_has_mic_control(pa_droid_hw_module *hw);
|
||||
int pa_droid_hw_mic_get_mute(pa_droid_hw_module *hw_module, bool *muted);
|
||||
void pa_droid_hw_mic_set_mute(pa_droid_hw_module *hw_module, bool muted);
|
||||
|
|
@ -304,6 +305,8 @@ int pa_droid_stream_set_route(pa_droid_stream *s, audio_devices_t device);
|
|||
pa_droid_stream *pa_droid_open_input_stream(pa_droid_hw_module *hw_module,
|
||||
const pa_sample_spec *requested_sample_spec,
|
||||
const pa_channel_map *requested_channel_map);
|
||||
bool pa_droid_hw_set_input_device(pa_droid_hw_module *hw_module,
|
||||
audio_devices_t device);
|
||||
|
||||
const pa_sample_spec *pa_droid_stream_sample_spec(pa_droid_stream *stream);
|
||||
const pa_channel_map *pa_droid_stream_channel_map(pa_droid_stream *stream);
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue