avcodec/h264_slice: Fix overflow in slice offset
[ffmpeg.git] / libavcodec / sipr_parser.c
1 /*
2  * This file is part of FFmpeg.
3  *
4  * FFmpeg is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU Lesser General Public
6  * License as published by the Free Software Foundation; either
7  * version 2.1 of the License, or (at your option) any later version.
8  *
9  * FFmpeg is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12  * Lesser General Public License for more details.
13  *
14  * You should have received a copy of the GNU Lesser General Public
15  * License along with FFmpeg; if not, write to the Free Software
16  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
17  */
18
19 /**
20  * @file
21  * Sipr audio parser
22  */
23
24 #include "parser.h"
25
26 typedef struct SiprParserContext{
27     ParseContext pc;
28 } SiprParserContext;
29
30 static int sipr_split(AVCodecContext *avctx, const uint8_t *buf, int buf_size)
31 {
32     int next;
33
34     switch (avctx->block_align) {
35     case 20:
36     case 19:
37     case 29:
38     case 37: next = avctx->block_align; break;
39     default:
40         if      (avctx->bit_rate > 12200) next = 20;
41         else if (avctx->bit_rate > 7500 ) next = 19;
42         else if (avctx->bit_rate > 5750 ) next = 29;
43         else                              next = 37;
44     }
45
46     return FFMIN(next, buf_size);
47 }
48
49 static int sipr_parse(AVCodecParserContext *s1, AVCodecContext *avctx,
50                       const uint8_t **poutbuf, int *poutbuf_size,
51                       const uint8_t *buf, int buf_size)
52 {
53     SiprParserContext *s = s1->priv_data;
54     ParseContext *pc = &s->pc;
55     int next;
56
57     next = sipr_split(avctx, buf, buf_size);
58     if (ff_combine_frame(pc, next, &buf, &buf_size) < 0) {
59         *poutbuf = NULL;
60         *poutbuf_size = 0;
61         return buf_size;
62     }
63
64     *poutbuf      = buf;
65     *poutbuf_size = buf_size;
66     return next;
67 }
68
69 AVCodecParser ff_sipr_parser = {
70     .codec_ids      = { AV_CODEC_ID_SIPR },
71     .priv_data_size = sizeof(SiprParserContext),
72     .parser_parse   = sipr_parse,
73     .parser_close   = ff_parse_close,
74 };