2 * Copyright (C) 2008 David Conrad
4 * This file is part of Libav.
6 * Libav is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * Libav is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with Libav; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
21 #include <speex/speex.h>
22 #include <speex/speex_header.h>
23 #include <speex/speex_stereo.h>
24 #include <speex/speex_callbacks.h>
26 #include "libavutil/channel_layout.h"
27 #include "libavutil/common.h"
33 SpeexStereoState stereo
;
39 static av_cold
int libspeex_decode_init(AVCodecContext
*avctx
)
41 LibSpeexContext
*s
= avctx
->priv_data
;
42 const SpeexMode
*mode
;
43 SpeexHeader
*header
= NULL
;
46 avctx
->sample_fmt
= AV_SAMPLE_FMT_S16
;
47 if (avctx
->extradata
&& avctx
->extradata_size
>= 80) {
48 header
= speex_packet_to_header(avctx
->extradata
,
49 avctx
->extradata_size
);
51 av_log(avctx
, AV_LOG_WARNING
, "Invalid Speex header\n");
54 avctx
->channels
= header
->nb_channels
;
55 spx_mode
= header
->mode
;
56 speex_header_free(header
);
58 switch (avctx
->sample_rate
) {
59 case 8000: spx_mode
= 0; break;
60 case 16000: spx_mode
= 1; break;
61 case 32000: spx_mode
= 2; break;
63 /* libspeex can handle any mode if initialized as ultra-wideband */
64 av_log(avctx
, AV_LOG_WARNING
, "Invalid sample rate: %d\n"
65 "Decoding as 32kHz ultra-wideband\n",
71 mode
= speex_lib_get_mode(spx_mode
);
73 av_log(avctx
, AV_LOG_ERROR
, "Unknown Speex mode %d", spx_mode
);
74 return AVERROR_INVALIDDATA
;
76 avctx
->sample_rate
= 8000 << spx_mode
;
77 s
->frame_size
= 160 << spx_mode
;
79 if (avctx
->channels
< 1 || avctx
->channels
> 2) {
80 /* libspeex can handle mono or stereo if initialized as stereo */
81 av_log(avctx
, AV_LOG_ERROR
, "Invalid channel count: %d.\n"
82 "Decoding as stereo.\n", avctx
->channels
);
85 avctx
->channel_layout
= avctx
->channels
== 2 ? AV_CH_LAYOUT_STEREO
:
88 speex_bits_init(&s
->bits
);
89 s
->dec_state
= speex_decoder_init(mode
);
91 av_log(avctx
, AV_LOG_ERROR
, "Error initializing libspeex decoder.\n");
95 if (avctx
->channels
== 2) {
96 SpeexCallback callback
;
97 callback
.callback_id
= SPEEX_INBAND_STEREO
;
98 callback
.func
= speex_std_stereo_request_handler
;
99 callback
.data
= &s
->stereo
;
100 s
->stereo
= (SpeexStereoState
)SPEEX_STEREO_STATE_INIT
;
101 speex_decoder_ctl(s
->dec_state
, SPEEX_SET_HANDLER
, &callback
);
107 static int libspeex_decode_frame(AVCodecContext
*avctx
, void *data
,
108 int *got_frame_ptr
, AVPacket
*avpkt
)
110 uint8_t *buf
= avpkt
->data
;
111 int buf_size
= avpkt
->size
;
112 LibSpeexContext
*s
= avctx
->priv_data
;
113 AVFrame
*frame
= data
;
115 int ret
, consumed
= 0;
117 /* get output buffer */
118 frame
->nb_samples
= s
->frame_size
;
119 if ((ret
= ff_get_buffer(avctx
, frame
, 0)) < 0) {
120 av_log(avctx
, AV_LOG_ERROR
, "get_buffer() failed\n");
123 output
= (int16_t *)frame
->data
[0];
125 /* if there is not enough data left for the smallest possible frame or the
126 next 5 bits are a terminator code, reset the libspeex buffer using the
127 current packet, otherwise ignore the current packet and keep decoding
128 frames from the libspeex buffer. */
129 if (speex_bits_remaining(&s
->bits
) < 5 ||
130 speex_bits_peek_unsigned(&s
->bits
, 5) == 0x1F) {
131 /* check for flush packet */
132 if (!buf
|| !buf_size
) {
137 speex_bits_read_from(&s
->bits
, buf
, buf_size
);
141 /* decode a single frame */
142 ret
= speex_decode_int(s
->dec_state
, &s
->bits
, output
);
144 av_log(avctx
, AV_LOG_ERROR
, "Error decoding Speex frame.\n");
145 return AVERROR_INVALIDDATA
;
147 if (avctx
->channels
== 2)
148 speex_decode_stereo_int(output
, s
->frame_size
, &s
->stereo
);
155 static av_cold
int libspeex_decode_close(AVCodecContext
*avctx
)
157 LibSpeexContext
*s
= avctx
->priv_data
;
159 speex_bits_destroy(&s
->bits
);
160 speex_decoder_destroy(s
->dec_state
);
165 static av_cold
void libspeex_decode_flush(AVCodecContext
*avctx
)
167 LibSpeexContext
*s
= avctx
->priv_data
;
168 speex_bits_reset(&s
->bits
);
171 AVCodec ff_libspeex_decoder
= {
173 .type
= AVMEDIA_TYPE_AUDIO
,
174 .id
= AV_CODEC_ID_SPEEX
,
175 .priv_data_size
= sizeof(LibSpeexContext
),
176 .init
= libspeex_decode_init
,
177 .close
= libspeex_decode_close
,
178 .decode
= libspeex_decode_frame
,
179 .flush
= libspeex_decode_flush
,
180 .capabilities
= CODEC_CAP_SUBFRAMES
| CODEC_CAP_DELAY
| CODEC_CAP_DR1
,
181 .long_name
= NULL_IF_CONFIG_SMALL("libspeex Speex"),