On Mon, 29 May 2017 20:39:55 +0200, plevine457@xxxxxxxxx wrote: > > From: Peter Levine <plevine457@xxxxxxxxx> > > Signed-off-by: Peter Levine <plevine457@xxxxxxxxx> Hmm, the patch does what's far more than here written. Can we avoid the file rename? The rename makes it a complete refresh, so essentially it look as you wrote everything from scratch. thanks, Takashi > > diff --git a/Makefile.am b/Makefile.am > index 69cfe0d..9195b56 100644 > --- a/Makefile.am > +++ b/Makefile.am > @@ -9,8 +9,14 @@ if HAVE_SAMPLERATE > SUBDIRS += rate > endif > if HAVE_AVCODEC > +SUBDIRS += a52 > +if !HAVE_AVRESAMPLE > SUBDIRS += a52 rate-lavc > endif > +endif > +if HAVE_AVRESAMPLE > +SUBDIRS += rate-lavr > +endif > if HAVE_MAEMO_PLUGIN > SUBDIRS += maemo > endif > diff --git a/configure.ac b/configure.ac > index f42601c..0af5ec9 100644 > --- a/configure.ac > +++ b/configure.ac > @@ -127,6 +127,10 @@ if test $HAVE_AVCODEC = yes; then > if test -z "$AVCODEC_HEADER"; then > HAVE_AVCODEC=no > fi > + SAVE_LIBS=$LIBS > + LIBS="$LIBS $AVCODEC_LIBS" > + AC_CHECK_FUNCS([av_resample_init]) > + LIBS=$SAVE_LIBS > CFLAGS="$CFLAGS_saved" > fi > > @@ -135,6 +139,18 @@ AC_SUBST(AVCODEC_CFLAGS) > AC_SUBST(AVCODEC_LIBS) > AC_SUBST(AVCODEC_HEADER) > > +AC_ARG_ENABLE([avresample], > + AS_HELP_STRING([--disable-avresample], [Do not build plugins depending on avcodec (lavrate)])) > + > +if test "x$enable_avresample" != "xno"; then > + PKG_CHECK_MODULES(AVRESAMPLE, [libavresample libavutil], [HAVE_AVRESAMPLE=yes], [HAVE_AVRESAMPLE=no]) > +fi > + > +AM_CONDITIONAL(HAVE_AVRESAMPLE, test x$HAVE_AVCODEC = xyes) > +AC_SUBST(AVRESAMPLE_CFLAGS) > +AC_SUBST(AVRESAMPLE_LIBS) > +AC_SUBST(AVRESAMPLE_HEADER) > + > AC_ARG_ENABLE([speexdsp], > AS_HELP_STRING([--disable-speexdsp], [Disable building of speexdsp plugin])) > > @@ -217,7 +233,7 @@ AC_OUTPUT([ > mix/Makefile > rate/Makefile > a52/Makefile > - rate-lavc/Makefile > + rate-lavr/Makefile > maemo/Makefile > doc/Makefile > usb_stream/Makefile > diff --git a/rate-lavr/Makefile.am b/rate-lavr/Makefile.am > new file mode 100644 > index 0000000..a1dca35 > --- /dev/null > +++ b/rate-lavr/Makefile.am > @@ -0,0 +1,22 @@ > +asound_module_rate_lavr_LTLIBRARIES = libasound_module_rate_lavr.la > + > +asound_module_rate_lavrdir = @ALSA_PLUGIN_DIR@ > + > +AM_CFLAGS = -Wall -g @ALSA_CFLAGS@ @AVRESAMPLE_CFLAGS@ > +AM_LDFLAGS = -module -avoid-version -export-dynamic -no-undefined $(LDFLAGS_NOUNDEFINED) > + > +libasound_module_rate_lavr_la_SOURCES = rate_lavr.c > +libasound_module_rate_lavr_la_LIBADD = @ALSA_LIBS@ @AVRESAMPLE_LIBS@ > + > + > +install-exec-hook: > + rm -f $(DESTDIR)@ALSA_PLUGIN_DIR@/libasound_module_rate_lavcrate*.so > + $(LN_S) libasound_module_rate_lavr.so $(DESTDIR)@ALSA_PLUGIN_DIR@/libasound_module_rate_lavcrate.so > + $(LN_S) libasound_module_rate_lavr.so $(DESTDIR)@ALSA_PLUGIN_DIR@/libasound_module_rate_lavcrate_higher.so > + $(LN_S) libasound_module_rate_lavr.so $(DESTDIR)@ALSA_PLUGIN_DIR@/libasound_module_rate_lavcrate_high.so > + $(LN_S) libasound_module_rate_lavr.so $(DESTDIR)@ALSA_PLUGIN_DIR@/libasound_module_rate_lavcrate_fast.so > + $(LN_S) libasound_module_rate_lavr.so $(DESTDIR)@ALSA_PLUGIN_DIR@/libasound_module_rate_lavcrate_faster.so > + > +uninstall-hook: > + rm -f $(DESTDIR)@ALSA_PLUGIN_DIR@/libasound_module_rate_lavcrate*.so > + rm -f $(DESTDIR)@ALSA_PLUGIN_DIR@/libasound_module_rate_lavr*.so > diff --git a/rate-lavr/rate_lavr.c b/rate-lavr/rate_lavr.c > new file mode 100644 > index 0000000..fe3bf4b > --- /dev/null > +++ b/rate-lavr/rate_lavr.c > @@ -0,0 +1,227 @@ > +/* > + * Rate converter plugin using libavresample > + * Copyright (c) 2014 by Anton Khirnov > + * > + * This library is free software; you can redistribute it and/or > + * modify it under the terms of the GNU Lesser General Public > + * License as published by the Free Software Foundation; either > + * version 2.1 of the License, or (at your option) any later version. > + * > + * This library is distributed in the hope that it will be useful, > + * but WITHOUT ANY WARRANTY; without even the implied warranty of > + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU > + * Lesser General Public License for more details. > + */ > + > +#include <stdio.h> > +#include <alsa/asoundlib.h> > +#include <alsa/pcm_rate.h> > + > +#include <libavresample/avresample.h> > +#include <libavutil/channel_layout.h> > +#include <libavutil/opt.h> > +#include <libavutil/mathematics.h> > +#include <libavutil/samplefmt.h> > + > + > +static int filter_size = 16; > +static int phase_shift = 10; /* auto-adjusts */ > +static double cutoff = 0; /* auto-adjusts */ > + > +struct rate_src { > + AVAudioResampleContext *avr; > + > + int in_rate; > + int out_rate; > + unsigned int channels; > +}; > + > +static snd_pcm_uframes_t input_frames(void *obj, snd_pcm_uframes_t frames) > +{ > + return frames; > +} > + > +static snd_pcm_uframes_t output_frames(void *obj, snd_pcm_uframes_t frames) > +{ > + return frames; > +} > + > +static void pcm_src_free(void *obj) > +{ > + struct rate_src *rate = obj; > + avresample_free(&rate->avr); > +} > + > +static int pcm_src_init(void *obj, snd_pcm_rate_info_t *info) > +{ > + struct rate_src *rate = obj; > + int i, ir, or; > + > + if (!rate->avr || rate->channels != info->channels) { > + int ret; > + > + pcm_src_free(rate); > + rate->channels = info->channels; > + ir = rate->in_rate = info->in.rate; > + or = rate->out_rate = info->out.rate; > + i = av_gcd(or, ir); > + if (or > ir) { > + phase_shift = or/i; > + } else { > + phase_shift = ir/i; > + } > + if (cutoff <= 0.0) { > + cutoff = 1.0 - 1.0/filter_size; > + if (cutoff < 0.80) > + cutoff = 0.80; > + } > + > + rate->avr = avresample_alloc_context(); > + if (!rate->avr) > + return -ENOMEM; > + > + av_opt_set_int(rate->avr, "in_sample_rate", info->in.rate, 0); > + av_opt_set_int(rate->avr, "out_sample_rate", info->out.rate, 0); > + av_opt_set_int(rate->avr, "in_sample_format", AV_SAMPLE_FMT_S16, 0); > + av_opt_set_int(rate->avr, "out_sample_format", AV_SAMPLE_FMT_S16, 0); > + av_opt_set_int(rate->avr, "in_channel_layout", av_get_default_channel_layout(rate->channels), 0); > + av_opt_set_int(rate->avr, "out_channel_layout", av_get_default_channel_layout(rate->channels), 0); > + > + av_opt_set_int(rate->avr, "filter_size", filter_size, 0); > + av_opt_set_int(rate->avr, "phase_shift", phase_shift, 0); > + av_opt_set_double(rate->avr, "cutoff", cutoff, 0); > + > + ret = avresample_open(rate->avr); > + if (ret < 0) { > + avresample_free(&rate->avr); > + return -EINVAL; > + } > + } > + > + return 0; > +} > + > +static int pcm_src_adjust_pitch(void *obj, snd_pcm_rate_info_t *info) > +{ > + struct rate_src *rate = obj; > + > + if (info->out.rate != rate->out_rate || info->in.rate != rate->in_rate) > + pcm_src_init(obj, info); > + return 0; > +} > + > +static void pcm_src_reset(void *obj) > +{ > + struct rate_src *rate = obj; > + > + if (rate->avr) { > + avresample_close(rate->avr); > + avresample_open(rate->avr); > + } > +} > + > +static void pcm_src_convert_s16(void *obj, int16_t *dst, unsigned int > + dst_frames, const int16_t *src, unsigned int src_frames) > +{ > + struct rate_src *rate = obj; > + int consumed = 0, chans=rate->channels, ret=0, i; > + int total_in = avresample_get_delay(rate->avr) + src_frames; > + > + ret = avresample_convert(rate->avr, &dst, dst_frames * chans * 2, dst_frames, > + &src, src_frames * chans * 2, src_frames); > + > + avresample_set_compensation(rate->avr, > + total_in - src_frames > filter_size ? 0 : 1, src_frames); > +} > + > +static void pcm_src_close(void *obj) > +{ > + pcm_src_free(obj); > +} > + > +#if SND_PCM_RATE_PLUGIN_VERSION >= 0x010002 > +static int get_supported_rates(void *obj, unsigned int *rate_min, > + unsigned int *rate_max) > +{ > + *rate_min = *rate_max = 0; /* both unlimited */ > + return 0; > +} > + > +static void dump(void *obj, snd_output_t *out) > +{ > + snd_output_printf(out, "Converter: libavr\n"); > +} > +#endif > + > +static snd_pcm_rate_ops_t pcm_src_ops = { > + .close = pcm_src_close, > + .init = pcm_src_init, > + .free = pcm_src_free, > + .adjust_pitch = pcm_src_adjust_pitch, > + .convert_s16 = pcm_src_convert_s16, > + .input_frames = input_frames, > + .output_frames = output_frames, > +#if SND_PCM_RATE_PLUGIN_VERSION >= 0x010002 > + .version = SND_PCM_RATE_PLUGIN_VERSION, > + .get_supported_rates = get_supported_rates, > + .dump = dump, > +#endif > +}; > + > +int pcm_src_open(unsigned int version, void **objp, snd_pcm_rate_ops_t *ops) > + > +{ > + struct rate_src *rate; > + > +#if SND_PCM_RATE_PLUGIN_VERSION < 0x010002 > + if (version != SND_PCM_RATE_PLUGIN_VERSION) { > + fprintf(stderr, "Invalid rate plugin version %x\n", version); > + return -EINVAL; > + } > +#endif > + rate = calloc(1, sizeof(*rate)); > + if (!rate) > + return -ENOMEM; > + > + *objp = rate; > + rate->avr = NULL; > +#if SND_PCM_RATE_PLUGIN_VERSION >= 0x010002 > + if (version == 0x010001) > + memcpy(ops, &pcm_src_ops, sizeof(snd_pcm_rate_old_ops_t)); > + else > +#endif > + *ops = pcm_src_ops; > + return 0; > +} > + > +int SND_PCM_RATE_PLUGIN_ENTRY(lavcrate)(unsigned int version, void **objp, > + snd_pcm_rate_ops_t *ops) > +{ > + return pcm_src_open(version, objp, ops); > +} > +int SND_PCM_RATE_PLUGIN_ENTRY(lavcrate_higher)(unsigned int version, > + void **objp, snd_pcm_rate_ops_t *ops) > +{ > + filter_size = 64; > + return pcm_src_open(version, objp, ops); > +} > +int SND_PCM_RATE_PLUGIN_ENTRY(lavcrate_high)(unsigned int version, > + void **objp, snd_pcm_rate_ops_t *ops) > +{ > + filter_size = 32; > + return pcm_src_open(version, objp, ops); > +} > +int SND_PCM_RATE_PLUGIN_ENTRY(lavcrate_fast)(unsigned int version, > + void **objp, snd_pcm_rate_ops_t *ops) > +{ > + filter_size = 8; > + return pcm_src_open(version, objp, ops); > +} > +int SND_PCM_RATE_PLUGIN_ENTRY(lavcrate_faster)(unsigned int version, > + void **objp, snd_pcm_rate_ops_t *ops) > +{ > + filter_size = 4; > + return pcm_src_open(version, objp, ops); > +} > + > + > -- > 2.13.0 > _______________________________________________ Alsa-devel mailing list Alsa-devel@xxxxxxxxxxxxxxxx http://mailman.alsa-project.org/mailman/listinfo/alsa-devel