diff --git a/libavcodec/arm/Makefile b/libavcodec/arm/Makefile index 1e08569066..240ee3f563 100644 --- a/libavcodec/arm/Makefile +++ b/libavcodec/arm/Makefile @@ -32,6 +32,8 @@ OBJS-$(CONFIG_VP3DSP) += arm/vp3dsp_init_arm.o # decoders/encoders OBJS-$(CONFIG_AAC_DECODER) += arm/aacpsdsp_init_arm.o \ arm/sbrdsp_init_arm.o +OBJS-$(CONFIG_ADPCM_G722_DECODER) += arm/g722dsp_init_arm.o +OBJS-$(CONFIG_ADPCM_G722_ENCODER) += arm/g722dsp_init_arm.o OBJS-$(CONFIG_DCA_DECODER) += arm/dcadsp_init_arm.o OBJS-$(CONFIG_FLAC_DECODER) += arm/flacdsp_init_arm.o \ arm/flacdsp_arm.o @@ -129,6 +131,8 @@ NEON-OBJS-$(CONFIG_VP3DSP) += arm/vp3dsp_neon.o # decoders/encoders NEON-OBJS-$(CONFIG_AAC_DECODER) += arm/aacpsdsp_neon.o \ arm/sbrdsp_neon.o +NEON-OBJS-$(CONFIG_ADPCM_G722_DECODER) += arm/g722dsp_neon.o +NEON-OBJS-$(CONFIG_ADPCM_G722_ENCODER) += arm/g722dsp_neon.o NEON-OBJS-$(CONFIG_LLAUDDSP) += arm/lossless_audiodsp_neon.o NEON-OBJS-$(CONFIG_DCA_DECODER) += arm/dcadsp_neon.o \ arm/synth_filter_neon.o diff --git a/libavcodec/arm/g722dsp_init_arm.c b/libavcodec/arm/g722dsp_init_arm.c new file mode 100644 index 0000000000..c0e5d8b989 --- /dev/null +++ b/libavcodec/arm/g722dsp_init_arm.c @@ -0,0 +1,35 @@ +/* + * Copyright (c) 2015 Peter Meerwald + * + * This file is part of FFmpeg. + * + * FFmpeg 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. + * + * FFmpeg 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. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#include + +#include "libavutil/attributes.h" +#include "libavutil/arm/cpu.h" +#include "libavcodec/g722dsp.h" + +extern void ff_g722_apply_qmf_neon(const int16_t *prev_samples, int xout[2]); + +av_cold void ff_g722dsp_init_arm(G722DSPContext *dsp) +{ + int cpu_flags = av_get_cpu_flags(); + + if (have_neon(cpu_flags)) + dsp->apply_qmf = ff_g722_apply_qmf_neon; +} diff --git a/libavcodec/arm/g722dsp_neon.S b/libavcodec/arm/g722dsp_neon.S new file mode 100644 index 0000000000..757e53f167 --- /dev/null +++ b/libavcodec/arm/g722dsp_neon.S @@ -0,0 +1,69 @@ +/* + * ARM NEON optimised DSP functions for G722 coding + * Copyright (c) 2015 Peter Meerwald + * + * This file is part of FFmpeg. + * + * FFmpeg 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. + * + * FFmpeg 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. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#include "libavutil/arm/asm.S" + +function ff_g722_apply_qmf_neon, export=1, align=4 + movrel r3, qmf_coeffs + vld1.s16 {d2,d3,d4}, [r0]! /* load prev_samples */ + vld1.s16 {d16,d17,d18}, [r3,:64]! /* load qmf_coeffs */ + vmull.s16 q0, d2, d16 + vmlal.s16 q0, d3, d17 + vmlal.s16 q0, d4, d18 + + vld1.s16 {d5,d6,d7}, [r0]! /* load prev_samples */ + vld1.s16 {d19,d20,d21}, [r3,:64]! /* load qmf_coeffs */ + vmlal.s16 q0, d5, d19 + vmlal.s16 q0, d6, d20 + vmlal.s16 q0, d7, d21 + + vadd.s32 d0, d1, d0 + vrev64.32 d0, d0 + vst1.s32 {d0}, [r1] + bx lr +endfunc + +const qmf_coeffs, align=4 + .hword 3 + .hword -11 + .hword -11 + .hword 53 + .hword 12 + .hword -156 + .hword 32 + .hword 362 + .hword -210 + .hword -805 + .hword 951 + .hword 3876 + .hword 3876 + .hword 951 + .hword -805 + .hword -210 + .hword 362 + .hword 32 + .hword -156 + .hword 12 + .hword 53 + .hword -11 + .hword -11 + .hword 3 +endconst diff --git a/libavcodec/g722dsp.c b/libavcodec/g722dsp.c index 0416d22ea3..051f89191d 100644 --- a/libavcodec/g722dsp.c +++ b/libavcodec/g722dsp.c @@ -68,4 +68,7 @@ static void g722_apply_qmf(const int16_t *prev_samples, int xout[2]) av_cold void ff_g722dsp_init(G722DSPContext *c) { c->apply_qmf = g722_apply_qmf; + + if (ARCH_ARM) + ff_g722dsp_init_arm(c); } diff --git a/libavcodec/g722dsp.h b/libavcodec/g722dsp.h index 210e107c79..cab4a5f7f2 100644 --- a/libavcodec/g722dsp.h +++ b/libavcodec/g722dsp.h @@ -28,5 +28,6 @@ typedef struct G722DSPContext { } G722DSPContext; void ff_g722dsp_init(G722DSPContext *c); +void ff_g722dsp_init_arm(G722DSPContext *c); #endif /* AVCODEC_G722DSP_H */