[pulseaudio-discuss] [PATCH 4/6] lfe-filter: change the crossover frequency as a parameter

Alexander E. Patrakov patrakov at gmail.com
Sun Feb 1 07:18:58 PST 2015


29.01.2015 03:14, David Henningsson wrote:
> From: Hui Wang <hui.wang at canonical.com>
>
> Add a user defined parameter lfe-crossover-freq for the lfe-filter,
> to pass this parameter to the lfe-filter, we need to change the
> pa_resampler_new() API as well.

OK for now, but for a perfectionist inside me, this looks too global for 
a preference. E.g., on a laptop that has internal 5.1 speakers, I would 
imagine wanting it for the internal speakers but not for the HDMI output.

>
> Signed-off-by: Hui Wang <hui.wang at canonical.com>
> ---
>   man/pulse-daemon.conf.5.xml.in             | 5 +++++
>   src/daemon/daemon-conf.c                   | 3 +++
>   src/daemon/daemon-conf.h                   | 1 +
>   src/daemon/daemon.conf.in                  | 1 +
>   src/daemon/main.c                          | 1 +
>   src/modules/module-virtual-surround-sink.c | 2 +-
>   src/pulsecore/core.c                       | 1 +
>   src/pulsecore/core.h                       | 1 +
>   src/pulsecore/resampler.c                  | 6 +++---
>   src/pulsecore/resampler.h                  | 1 +
>   src/pulsecore/sink-input.c                 | 2 ++
>   src/pulsecore/source-output.c              | 2 ++
>   src/tests/remix-test.c                     | 3 ++-
>   src/tests/resampler-test.c                 | 7 ++++---
>   14 files changed, 28 insertions(+), 8 deletions(-)
>
> diff --git a/man/pulse-daemon.conf.5.xml.in b/man/pulse-daemon.conf.5.xml.in
> index 8c99e9c..49c75a6 100644
> --- a/man/pulse-daemon.conf.5.xml.in
> +++ b/man/pulse-daemon.conf.5.xml.in
> @@ -121,6 +121,11 @@ License along with PulseAudio; if not, see <http://www.gnu.org/licenses/>.
>       </option>
>
>       <option>
> +      <p><opt>lfe-crossover-freq=</opt> The crossover frequency (in Hz) for the
> +      LFE filter. Defaults to 120 Hz.</p>
> +    </option>
> +
> +    <option>
>         <p><opt>use-pid-file=</opt> Create a PID file in the runtime directory
>         (<file>$XDG_RUNTIME_DIR/pulse/pid</file>). If this is enabled you may
>         use commands like <opt>--kill</opt> or <opt>--check</opt>. If
> diff --git a/src/daemon/daemon-conf.c b/src/daemon/daemon-conf.c
> index 61cf630..21a8edb 100644
> --- a/src/daemon/daemon-conf.c
> +++ b/src/daemon/daemon-conf.c
> @@ -83,6 +83,7 @@ static const pa_daemon_conf default_conf = {
>       .resample_method = PA_RESAMPLER_AUTO,
>       .disable_remixing = false,
>       .disable_lfe_remixing = false,
> +    .lfe_crossover_freq = 120,
>       .config_file = NULL,
>       .use_pid_file = true,
>       .system_instance = false,
> @@ -553,6 +554,7 @@ int pa_daemon_conf_load(pa_daemon_conf *c, const char *filename) {
>           { "enable-remixing",            pa_config_parse_not_bool, &c->disable_remixing, NULL },
>           { "disable-lfe-remixing",       pa_config_parse_bool,     &c->disable_lfe_remixing, NULL },
>           { "enable-lfe-remixing",        pa_config_parse_not_bool, &c->disable_lfe_remixing, NULL },
> +        { "lfe-crossover-freq",         pa_config_parse_unsigned, &c->lfe_crossover_freq, NULL },
>           { "load-default-script-file",   pa_config_parse_bool,     &c->load_default_script_file, NULL },
>           { "shm-size-bytes",             pa_config_parse_size,     &c->shm_size, NULL },
>           { "log-meta",                   pa_config_parse_bool,     &c->log_meta, NULL },
> @@ -745,6 +747,7 @@ char *pa_daemon_conf_dump(pa_daemon_conf *c) {
>       pa_strbuf_printf(s, "resample-method = %s\n", pa_resample_method_to_string(c->resample_method));
>       pa_strbuf_printf(s, "enable-remixing = %s\n", pa_yes_no(!c->disable_remixing));
>       pa_strbuf_printf(s, "enable-lfe-remixing = %s\n", pa_yes_no(!c->disable_lfe_remixing));
> +    pa_strbuf_printf(s, "lfe-crossover-freq = %u\n", c->lfe_crossover_freq);
>       pa_strbuf_printf(s, "default-sample-format = %s\n", pa_sample_format_to_string(c->default_sample_spec.format));
>       pa_strbuf_printf(s, "default-sample-rate = %u\n", c->default_sample_spec.rate);
>       pa_strbuf_printf(s, "alternate-sample-rate = %u\n", c->alternate_sample_rate);
> diff --git a/src/daemon/daemon-conf.h b/src/daemon/daemon-conf.h
> index 62587b2..458784c 100644
> --- a/src/daemon/daemon-conf.h
> +++ b/src/daemon/daemon-conf.h
> @@ -127,6 +127,7 @@ typedef struct pa_daemon_conf {
>       unsigned default_n_fragments, default_fragment_size_msec;
>       unsigned deferred_volume_safety_margin_usec;
>       int deferred_volume_extra_delay_usec;
> +    unsigned lfe_crossover_freq;
>       pa_sample_spec default_sample_spec;
>       uint32_t alternate_sample_rate;
>       pa_channel_map default_channel_map;
> diff --git a/src/daemon/daemon.conf.in b/src/daemon/daemon.conf.in
> index 26908df..b48afa2 100644
> --- a/src/daemon/daemon.conf.in
> +++ b/src/daemon/daemon.conf.in
> @@ -55,6 +55,7 @@ ifelse(@HAVE_DBUS@, 1, [dnl
>   ; resample-method = speex-float-1
>   ; enable-remixing = yes
>   ; enable-lfe-remixing = yes
> +; lfe-crossover-freq = 120
>
>   ; flat-volumes = yes
>
> diff --git a/src/daemon/main.c b/src/daemon/main.c
> index 68ed383..deb1e43 100644
> --- a/src/daemon/main.c
> +++ b/src/daemon/main.c
> @@ -1029,6 +1029,7 @@ int main(int argc, char *argv[]) {
>       c->default_fragment_size_msec = conf->default_fragment_size_msec;
>       c->deferred_volume_safety_margin_usec = conf->deferred_volume_safety_margin_usec;
>       c->deferred_volume_extra_delay_usec = conf->deferred_volume_extra_delay_usec;
> +    c->lfe_crossover_freq = conf->lfe_crossover_freq;
>       c->exit_idle_time = conf->exit_idle_time;
>       c->scache_idle_time = conf->scache_idle_time;
>       c->resample_method = conf->resample_method;
> diff --git a/src/modules/module-virtual-surround-sink.c b/src/modules/module-virtual-surround-sink.c
> index 8f05f53..6c7120a 100644
> --- a/src/modules/module-virtual-surround-sink.c
> +++ b/src/modules/module-virtual-surround-sink.c
> @@ -743,7 +743,7 @@ int pa__init(pa_module*m) {
>       pa_memblock_unref(silence.memblock);
>
>       /* resample hrir */
> -    resampler = pa_resampler_new(u->sink->core->mempool, &hrir_temp_ss, &hrir_map, &hrir_ss, &hrir_map,
> +    resampler = pa_resampler_new(u->sink->core->mempool, &hrir_temp_ss, &hrir_map, &hrir_ss, &hrir_map, u->sink->core->lfe_crossover_freq,
>                                    PA_RESAMPLER_SRC_SINC_BEST_QUALITY, PA_RESAMPLER_NO_REMAP);
>
>       u->hrir_samples = hrir_temp_chunk.length / pa_frame_size(&hrir_temp_ss) * hrir_ss.rate / hrir_temp_ss.rate;
> diff --git a/src/pulsecore/core.c b/src/pulsecore/core.c
> index 0e67005..0e63bac 100644
> --- a/src/pulsecore/core.c
> +++ b/src/pulsecore/core.c
> @@ -144,6 +144,7 @@ pa_core* pa_core_new(pa_mainloop_api *m, bool shared, size_t shm_size) {
>       c->realtime_priority = 5;
>       c->disable_remixing = false;
>       c->disable_lfe_remixing = false;
> +    c->lfe_crossover_freq = 120;
>       c->deferred_volume = true;
>       c->resample_method = PA_RESAMPLER_SPEEX_FLOAT_BASE + 1;
>
> diff --git a/src/pulsecore/core.h b/src/pulsecore/core.h
> index 7d896bb..8570d47 100644
> --- a/src/pulsecore/core.h
> +++ b/src/pulsecore/core.h
> @@ -160,6 +160,7 @@ struct pa_core {
>       unsigned default_n_fragments, default_fragment_size_msec;
>       unsigned deferred_volume_safety_margin_usec;
>       int deferred_volume_extra_delay_usec;
> +    unsigned lfe_crossover_freq;
>
>       pa_defer_event *module_defer_unload_event;
>       pa_hashmap *modules_pending_unload; /* pa_module -> pa_module (hashmap-as-a-set) */
> diff --git a/src/pulsecore/resampler.c b/src/pulsecore/resampler.c
> index 34e58e4..8e07c73 100644
> --- a/src/pulsecore/resampler.c
> +++ b/src/pulsecore/resampler.c
> @@ -298,6 +298,7 @@ pa_resampler* pa_resampler_new(
>           const pa_channel_map *am,
>           const pa_sample_spec *b,
>           const pa_channel_map *bm,
> +	unsigned crossover_freq,
>           pa_resample_method_t method,
>           pa_resample_flags_t flags) {
>
> @@ -396,9 +397,8 @@ pa_resampler* pa_resampler_new(
>       if (lfe_filter_required) {
>           pa_sample_spec wss = r->o_ss;
>           wss.format = r->work_format;
> -        /* TODO: Temporary code that sets crossover freq to 120 Hz. This should be a parameter */
> -        r->lfe_filter = pa_lfe_filter_new(&wss, &r->o_cm, 120.0f);
> -        pa_log_debug("  lfe filter activated (LR4 type)");
> +        r->lfe_filter = pa_lfe_filter_new(&wss, &r->o_cm, (float)crossover_freq);
> +        pa_log_debug("  lfe filter activated (LR4 type), the crossover_freq = %uHz", crossover_freq);
>       }
>
>       /* initialize implementation */
> diff --git a/src/pulsecore/resampler.h b/src/pulsecore/resampler.h
> index f60f3b1..c7a60a4 100644
> --- a/src/pulsecore/resampler.h
> +++ b/src/pulsecore/resampler.h
> @@ -115,6 +115,7 @@ pa_resampler* pa_resampler_new(
>           const pa_channel_map *am,
>           const pa_sample_spec *b,
>           const pa_channel_map *bm,
> +	unsigned crossover_freq,
>           pa_resample_method_t resample_method,
>           pa_resample_flags_t flags);
>
> diff --git a/src/pulsecore/sink-input.c b/src/pulsecore/sink-input.c
> index d95a93e..7d2202e 100644
> --- a/src/pulsecore/sink-input.c
> +++ b/src/pulsecore/sink-input.c
> @@ -451,6 +451,7 @@ int pa_sink_input_new(
>                             core->mempool,
>                             &data->sample_spec, &data->channel_map,
>                             &data->sink->sample_spec, &data->sink->channel_map,
> +                          core->lfe_crossover_freq,
>                             data->resample_method,
>                             ((data->flags & PA_SINK_INPUT_VARIABLE_RATE) ? PA_RESAMPLER_VARIABLE_RATE : 0) |
>                             ((data->flags & PA_SINK_INPUT_NO_REMAP) ? PA_RESAMPLER_NO_REMAP : 0) |
> @@ -2168,6 +2169,7 @@ int pa_sink_input_update_rate(pa_sink_input *i) {
>           new_resampler = pa_resampler_new(i->core->mempool,
>                                        &i->sample_spec, &i->channel_map,
>                                        &i->sink->sample_spec, &i->sink->channel_map,
> +                                     i->core->lfe_crossover_freq,
>                                        i->requested_resample_method,
>                                        ((i->flags & PA_SINK_INPUT_VARIABLE_RATE) ? PA_RESAMPLER_VARIABLE_RATE : 0) |
>                                        ((i->flags & PA_SINK_INPUT_NO_REMAP) ? PA_RESAMPLER_NO_REMAP : 0) |
> diff --git a/src/pulsecore/source-output.c b/src/pulsecore/source-output.c
> index c8090f7..4cc1053 100644
> --- a/src/pulsecore/source-output.c
> +++ b/src/pulsecore/source-output.c
> @@ -396,6 +396,7 @@ int pa_source_output_new(
>                           core->mempool,
>                           &data->source->sample_spec, &data->source->channel_map,
>                           &data->sample_spec, &data->channel_map,
> +                        core->lfe_crossover_freq,
>                           data->resample_method,
>                           ((data->flags & PA_SOURCE_OUTPUT_VARIABLE_RATE) ? PA_RESAMPLER_VARIABLE_RATE : 0) |
>                           ((data->flags & PA_SOURCE_OUTPUT_NO_REMAP) ? PA_RESAMPLER_NO_REMAP : 0) |
> @@ -1625,6 +1626,7 @@ int pa_source_output_update_rate(pa_source_output *o) {
>           new_resampler = pa_resampler_new(o->core->mempool,
>                                        &o->source->sample_spec, &o->source->channel_map,
>                                        &o->sample_spec, &o->channel_map,
> +                                     o->core->lfe_crossover_freq,
>                                        o->requested_resample_method,
>                                        ((o->flags & PA_SOURCE_OUTPUT_VARIABLE_RATE) ? PA_RESAMPLER_VARIABLE_RATE : 0) |
>                                        ((o->flags & PA_SOURCE_OUTPUT_NO_REMAP) ? PA_RESAMPLER_NO_REMAP : 0) |
> diff --git a/src/tests/remix-test.c b/src/tests/remix-test.c
> index 5193187..6feb8dc 100644
> --- a/src/tests/remix-test.c
> +++ b/src/tests/remix-test.c
> @@ -47,6 +47,7 @@ int main(int argc, char *argv[]) {
>
>       unsigned i, j;
>       pa_mempool *pool;
> +    unsigned crossover_freq = 120;
>
>       pa_log_set_level(PA_LOG_DEBUG);
>
> @@ -66,7 +67,7 @@ int main(int argc, char *argv[]) {
>               ss1.rate = ss2.rate = 44100;
>               ss1.format = ss2.format = PA_SAMPLE_S16NE;
>
> -            r = pa_resampler_new(pool, &ss1, &maps[i], &ss2, &maps[j], PA_RESAMPLER_AUTO, 0);
> +            r = pa_resampler_new(pool, &ss1, &maps[i], &ss2, &maps[j], crossover_freq, PA_RESAMPLER_AUTO, 0);
>
>               /* We don't really care for the resampler. We just want to
>                * see the remixing debug output. */
> diff --git a/src/tests/resampler-test.c b/src/tests/resampler-test.c
> index 96110fb..751d2dc 100644
> --- a/src/tests/resampler-test.c
> +++ b/src/tests/resampler-test.c
> @@ -303,6 +303,7 @@ int main(int argc, char *argv[]) {
>       bool all_formats = true;
>       pa_resample_method_t method;
>       int seconds;
> +    unsigned crossover_freq = 120;
>
>       static const struct option long_options[] = {
>           {"help",                  0, NULL, 'h'},
> @@ -419,7 +420,7 @@ int main(int argc, char *argv[]) {
>                      b.rate, b.channels, pa_sample_format_to_string(b.format));
>
>           ts = pa_rtclock_now();
> -        pa_assert_se(resampler = pa_resampler_new(pool, &a, NULL, &b, NULL, method, 0));
> +        pa_assert_se(resampler = pa_resampler_new(pool, &a, NULL, &b, NULL, crossover_freq, method, 0));
>           pa_log_info("init: %llu", (long long unsigned)(pa_rtclock_now() - ts));
>
>           i.memblock = pa_memblock_new(pool, pa_usec_to_bytes(1*PA_USEC_PER_SEC, &a));
> @@ -450,8 +451,8 @@ int main(int argc, char *argv[]) {
>                          pa_sample_format_to_string(b.format),
>                          pa_sample_format_to_string(a.format));
>
> -            pa_assert_se(forth = pa_resampler_new(pool, &a, NULL, &b, NULL, method, 0));
> -            pa_assert_se(back = pa_resampler_new(pool, &b, NULL, &a, NULL, method, 0));
> +            pa_assert_se(forth = pa_resampler_new(pool, &a, NULL, &b, NULL, crossover_freq, method, 0));
> +            pa_assert_se(back = pa_resampler_new(pool, &b, NULL, &a, NULL, crossover_freq, method, 0));
>
>               i.memblock = generate_block(pool, &a);
>               i.length = pa_memblock_get_length(i.memblock);
>

-- 
Alexander E. Patrakov


More information about the pulseaudio-discuss mailing list