2 * iLBC decoder/encoder stub
3 * Copyright (c) 2012 Martin Storsjo
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
24 #include "libavutil/channel_layout.h"
25 #include "libavutil/common.h"
26 #include "libavutil/opt.h"
30 static int get_mode(AVCodecContext
*avctx
)
32 if (avctx
->block_align
== 38)
34 else if (avctx
->block_align
== 50)
36 else if (avctx
->bit_rate
> 0)
37 return avctx
->bit_rate
<= 14000 ? 30 : 20;
42 typedef struct ILBCDecContext
{
45 iLBC_Dec_Inst_t decoder
;
49 static const AVOption ilbc_dec_options
[] = {
50 { "enhance", "Enhance the decoded audio (adds delay)", offsetof(ILBCDecContext
, enhance
), AV_OPT_TYPE_INT
, { .i64
= 0 }, 0, 1, AV_OPT_FLAG_AUDIO_PARAM
| AV_OPT_FLAG_DECODING_PARAM
},
54 static const AVClass ilbc_dec_class
= {
55 "libilbc", av_default_item_name
, ilbc_dec_options
, LIBAVUTIL_VERSION_INT
58 static av_cold
int ilbc_decode_init(AVCodecContext
*avctx
)
60 ILBCDecContext
*s
= avctx
->priv_data
;
63 if ((mode
= get_mode(avctx
)) < 0) {
64 av_log(avctx
, AV_LOG_ERROR
, "iLBC frame mode not indicated\n");
65 return AVERROR(EINVAL
);
68 WebRtcIlbcfix_InitDecode(&s
->decoder
, mode
, s
->enhance
);
69 avcodec_get_frame_defaults(&s
->frame
);
70 avctx
->coded_frame
= &s
->frame
;
73 avctx
->channel_layout
= AV_CH_LAYOUT_MONO
;
74 avctx
->sample_rate
= 8000;
75 avctx
->sample_fmt
= AV_SAMPLE_FMT_S16
;
80 static int ilbc_decode_frame(AVCodecContext
*avctx
, void *data
,
81 int *got_frame_ptr
, AVPacket
*avpkt
)
83 const uint8_t *buf
= avpkt
->data
;
84 int buf_size
= avpkt
->size
;
85 ILBCDecContext
*s
= avctx
->priv_data
;
88 if (s
->decoder
.no_of_bytes
> buf_size
) {
89 av_log(avctx
, AV_LOG_ERROR
, "iLBC frame too short (%u, should be %u)\n",
90 buf_size
, s
->decoder
.no_of_bytes
);
91 return AVERROR_INVALIDDATA
;
94 s
->frame
.nb_samples
= s
->decoder
.blockl
;
95 if ((ret
= ff_get_buffer(avctx
, &s
->frame
)) < 0) {
96 av_log(avctx
, AV_LOG_ERROR
, "get_buffer() failed\n");
100 WebRtcIlbcfix_DecodeImpl((WebRtc_Word16
*) s
->frame
.data
[0],
101 (const WebRtc_UWord16
*) buf
, &s
->decoder
, 1);
104 *(AVFrame
*)data
= s
->frame
;
106 return s
->decoder
.no_of_bytes
;
109 AVCodec ff_libilbc_decoder
= {
111 .type
= AVMEDIA_TYPE_AUDIO
,
112 .id
= AV_CODEC_ID_ILBC
,
113 .priv_data_size
= sizeof(ILBCDecContext
),
114 .init
= ilbc_decode_init
,
115 .decode
= ilbc_decode_frame
,
116 .capabilities
= CODEC_CAP_DR1
,
117 .long_name
= NULL_IF_CONFIG_SMALL("iLBC (Internet Low Bitrate Codec)"),
118 .priv_class
= &ilbc_dec_class
,
121 typedef struct ILBCEncContext
{
122 const AVClass
*class;
123 iLBC_Enc_Inst_t encoder
;
127 static const AVOption ilbc_enc_options
[] = {
128 { "mode", "iLBC mode (20 or 30 ms frames)", offsetof(ILBCEncContext
, mode
), AV_OPT_TYPE_INT
, { .i64
= 20 }, 20, 30, AV_OPT_FLAG_AUDIO_PARAM
| AV_OPT_FLAG_ENCODING_PARAM
},
132 static const AVClass ilbc_enc_class
= {
133 "libilbc", av_default_item_name
, ilbc_enc_options
, LIBAVUTIL_VERSION_INT
136 static av_cold
int ilbc_encode_init(AVCodecContext
*avctx
)
138 ILBCEncContext
*s
= avctx
->priv_data
;
141 if (avctx
->sample_rate
!= 8000) {
142 av_log(avctx
, AV_LOG_ERROR
, "Only 8000Hz sample rate supported\n");
143 return AVERROR(EINVAL
);
146 if (avctx
->channels
!= 1) {
147 av_log(avctx
, AV_LOG_ERROR
, "Only mono supported\n");
148 return AVERROR(EINVAL
);
151 if ((mode
= get_mode(avctx
)) > 0)
154 s
->mode
= s
->mode
!= 30 ? 20 : 30;
155 WebRtcIlbcfix_InitEncode(&s
->encoder
, s
->mode
);
157 avctx
->block_align
= s
->encoder
.no_of_bytes
;
158 avctx
->frame_size
= s
->encoder
.blockl
;
159 #if FF_API_OLD_ENCODE_AUDIO
160 avctx
->coded_frame
= avcodec_alloc_frame();
161 if (!avctx
->coded_frame
)
162 return AVERROR(ENOMEM
);
168 static av_cold
int ilbc_encode_close(AVCodecContext
*avctx
)
170 #if FF_API_OLD_ENCODE_AUDIO
171 av_freep(&avctx
->coded_frame
);
176 static int ilbc_encode_frame(AVCodecContext
*avctx
, AVPacket
*avpkt
,
177 const AVFrame
*frame
, int *got_packet_ptr
)
179 ILBCEncContext
*s
= avctx
->priv_data
;
182 if ((ret
= ff_alloc_packet(avpkt
, 50))) {
183 av_log(avctx
, AV_LOG_ERROR
, "Error getting output packet\n");
187 WebRtcIlbcfix_EncodeImpl((WebRtc_UWord16
*) avpkt
->data
, (const WebRtc_Word16
*) frame
->data
[0], &s
->encoder
);
189 avpkt
->size
= s
->encoder
.no_of_bytes
;
194 static const AVCodecDefault ilbc_encode_defaults
[] = {
199 AVCodec ff_libilbc_encoder
= {
201 .type
= AVMEDIA_TYPE_AUDIO
,
202 .id
= AV_CODEC_ID_ILBC
,
203 .priv_data_size
= sizeof(ILBCEncContext
),
204 .init
= ilbc_encode_init
,
205 .encode2
= ilbc_encode_frame
,
206 .close
= ilbc_encode_close
,
207 .sample_fmts
= (const enum AVSampleFormat
[]){ AV_SAMPLE_FMT_S16
,
208 AV_SAMPLE_FMT_NONE
},
209 .long_name
= NULL_IF_CONFIG_SMALL("iLBC (Internet Low Bitrate Codec)"),
210 .defaults
= ilbc_encode_defaults
,
211 .priv_class
= &ilbc_enc_class
,