2 * audio encoder psychoacoustic model
3 * Copyright (C) 2008 Konstantin Shishkov
5 * This file is part of Libav.
7 * Libav is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
12 * Libav is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with Libav; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
26 #include "iirfilter.h"
27 #include "libavutil/mem.h"
29 extern const FFPsyModel ff_aac_psy_model
;
31 av_cold
int ff_psy_init(FFPsyContext
*ctx
, AVCodecContext
*avctx
, int num_lens
,
32 const uint8_t **bands
, const int* num_bands
,
33 int num_groups
, const uint8_t *group_map
)
38 ctx
->ch
= av_mallocz(sizeof(ctx
->ch
[0]) * avctx
->channels
* 2);
39 ctx
->group
= av_mallocz(sizeof(ctx
->group
[0]) * num_groups
);
40 ctx
->bands
= av_malloc (sizeof(ctx
->bands
[0]) * num_lens
);
41 ctx
->num_bands
= av_malloc (sizeof(ctx
->num_bands
[0]) * num_lens
);
43 if (!ctx
->ch
|| !ctx
->group
|| !ctx
->bands
|| !ctx
->num_bands
) {
45 return AVERROR(ENOMEM
);
48 memcpy(ctx
->bands
, bands
, sizeof(ctx
->bands
[0]) * num_lens
);
49 memcpy(ctx
->num_bands
, num_bands
, sizeof(ctx
->num_bands
[0]) * num_lens
);
51 /* assign channels to groups (with virtual channels for coupling) */
52 for (i
= 0; i
< num_groups
; i
++) {
53 /* NOTE: Add 1 to handle the AAC chan_config without modification.
54 * This has the side effect of allowing an array of 0s to map
55 * to one channel per group.
57 ctx
->group
[i
].num_ch
= group_map
[i
] + 1;
58 for (j
= 0; j
< ctx
->group
[i
].num_ch
* 2; j
++)
59 ctx
->group
[i
].ch
[j
] = &ctx
->ch
[k
++];
62 switch (ctx
->avctx
->codec_id
) {
64 ctx
->model
= &ff_aac_psy_model
;
68 return ctx
->model
->init(ctx
);
72 FFPsyChannelGroup
*ff_psy_find_group(FFPsyContext
*ctx
, int channel
)
77 ch
+= ctx
->group
[i
++].num_ch
;
79 return &ctx
->group
[i
-1];
82 av_cold
void ff_psy_end(FFPsyContext
*ctx
)
86 av_freep(&ctx
->bands
);
87 av_freep(&ctx
->num_bands
);
88 av_freep(&ctx
->group
);
92 typedef struct FFPsyPreprocessContext
{
93 AVCodecContext
*avctx
;
95 struct FFIIRFilterCoeffs
*fcoeffs
;
96 struct FFIIRFilterState
**fstate
;
97 }FFPsyPreprocessContext
;
101 av_cold
struct FFPsyPreprocessContext
* ff_psy_preprocess_init(AVCodecContext
*avctx
)
103 FFPsyPreprocessContext
*ctx
;
105 float cutoff_coeff
= 0;
106 ctx
= av_mallocz(sizeof(FFPsyPreprocessContext
));
111 if (avctx
->cutoff
> 0)
112 cutoff_coeff
= 2.0 * avctx
->cutoff
/ avctx
->sample_rate
;
115 ctx
->fcoeffs
= ff_iir_filter_init_coeffs(avctx
, FF_FILTER_TYPE_BUTTERWORTH
,
116 FF_FILTER_MODE_LOWPASS
, FILT_ORDER
,
117 cutoff_coeff
, 0.0, 0.0);
119 ctx
->fstate
= av_mallocz(sizeof(ctx
->fstate
[0]) * avctx
->channels
);
124 for (i
= 0; i
< avctx
->channels
; i
++)
125 ctx
->fstate
[i
] = ff_iir_filter_init_state(FILT_ORDER
);
130 void ff_psy_preprocess(struct FFPsyPreprocessContext
*ctx
, float **audio
, int channels
)
133 int frame_size
= ctx
->avctx
->frame_size
;
136 for (ch
= 0; ch
< channels
; ch
++)
137 ff_iir_filter_flt(ctx
->fcoeffs
, ctx
->fstate
[ch
], frame_size
,
138 &audio
[ch
][frame_size
], 1, &audio
[ch
][frame_size
], 1);
142 av_cold
void ff_psy_preprocess_end(struct FFPsyPreprocessContext
*ctx
)
145 ff_iir_filter_free_coeffs(ctx
->fcoeffs
);
147 for (i
= 0; i
< ctx
->avctx
->channels
; i
++)
148 ff_iir_filter_free_state(ctx
->fstate
[i
]);
149 av_freep(&ctx
->fstate
);