summaryrefslogtreecommitdiff
path: root/libavcodec/flac.c
diff options
context:
space:
mode:
authorJustin Ruggles <justin.ruggles@gmail.com>2012-10-21 17:02:28 -0400
committerJustin Ruggles <justin.ruggles@gmail.com>2012-11-01 11:29:16 -0400
commit90fcac0e95b7d266c148a86506f301a2072d9de3 (patch)
tree3a98aa2c6d0bf7e22f78894dc5f308a7db0732d3 /libavcodec/flac.c
parent268f8ba112570956f1d7be8f4f2f0bea86c61461 (diff)
flacdec: allow mid-stream channel layout change
Although the libFLAC decoder cannot handle such a change, it is allowed by the spec and could potentially occur with live streams.
Diffstat (limited to 'libavcodec/flac.c')
-rw-r--r--libavcodec/flac.c19
1 files changed, 19 insertions, 0 deletions
diff --git a/libavcodec/flac.c b/libavcodec/flac.c
index d624beb61f..07da702e94 100644
--- a/libavcodec/flac.c
+++ b/libavcodec/flac.c
@@ -19,6 +19,7 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
+#include "libavutil/audioconvert.h"
#include "libavutil/crc.h"
#include "libavutil/log.h"
#include "bytestream.h"
@@ -28,6 +29,15 @@
static const int8_t sample_size_table[] = { 0, 8, 12, 0, 16, 20, 24, 0 };
+static const int64_t flac_channel_layouts[6] = {
+ AV_CH_LAYOUT_MONO,
+ AV_CH_LAYOUT_STEREO,
+ AV_CH_LAYOUT_SURROUND,
+ AV_CH_LAYOUT_QUAD,
+ AV_CH_LAYOUT_5POINT0,
+ AV_CH_LAYOUT_5POINT1
+};
+
static int64_t get_utf8(GetBitContext *gb)
{
int64_t val;
@@ -181,6 +191,14 @@ int avpriv_flac_is_extradata_valid(AVCodecContext *avctx,
return 1;
}
+void ff_flac_set_channel_layout(AVCodecContext *avctx)
+{
+ if (avctx->channels <= FF_ARRAY_ELEMS(flac_channel_layouts))
+ avctx->channel_layout = flac_channel_layouts[avctx->channels - 1];
+ else
+ avctx->channel_layout = 0;
+}
+
void avpriv_flac_parse_streaminfo(AVCodecContext *avctx, struct FLACStreaminfo *s,
const uint8_t *buffer)
{
@@ -205,6 +223,7 @@ void avpriv_flac_parse_streaminfo(AVCodecContext *avctx, struct FLACStreaminfo *
avctx->channels = s->channels;
avctx->sample_rate = s->samplerate;
avctx->bits_per_raw_sample = s->bps;
+ ff_flac_set_channel_layout(avctx);
s->samples = get_bits_long(&gb, 32) << 4;
s->samples |= get_bits(&gb, 4);