History

adx: move header decoding to ADX common code

Justin Ruggles committed 14 years ago

Commit d8cec2d1 parent 7ff55d93 files · +74 −36Browse files

Unified · Split

3 files
  1. libavcodec/adx.c +47 −0
  2. libavcodec/adx.h +21 −0
  3. libavcodec/adxdec.c +6 −36
libavcodec/adx.c+47−0
@@ -18,6 +18,7 @@ · 17 unmodified lines
18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19 */19 */
20 20
21#include "libavutil/intreadwrite.h"
21#include "libavutil/mathematics.h"22#include "libavutil/mathematics.h"
22#include "adx.h"23#include "adx.h"
23 24
@@ -32,3 +33,49 @@ void ff_adx_calculate_coeffs(int cutoff, int sample_rate, int bits, int *coeff) · 8 unmodified lines
32 coeff[0] = lrintf(c * 2.0 * (1 << bits));33 coeff[0] = lrintf(c * 2.0 * (1 << bits));
33 coeff[1] = lrintf(-(c * c) * (1 << bits));34 coeff[1] = lrintf(-(c * c) * (1 << bits));
34}35}
36
37int ff_adx_decode_header(AVCodecContext *avctx, const uint8_t *buf, int bufsize,
38 int *header_size, int *coeff)
39{
40 int offset, cutoff;
41
42 if (bufsize < 24)
43 return AVERROR_INVALIDDATA;
44
45 if (AV_RB16(buf) != 0x8000)
46 return AVERROR_INVALIDDATA;
47 offset = AV_RB16(buf + 2) + 4;
48
49 /* if copyright string is within the provided data, validate it */
50 if (bufsize >= offset && memcmp(buf + offset - 6, "(c)CRI", 6))
51 return AVERROR_INVALIDDATA;
52
53 /* check for encoding=3 block_size=18, sample_size=4 */
54 if (buf[4] != 3 || buf[5] != 18 || buf[6] != 4) {
55 av_log_ask_for_sample(avctx, "unsupported ADX format\n");
56 return AVERROR_PATCHWELCOME;
57 }
58
59 /* channels */
60 avctx->channels = buf[7];
61 if (avctx->channels > 2)
62 return AVERROR_INVALIDDATA;
63
64 /* sample rate */
65 avctx->sample_rate = AV_RB32(buf + 8);
66 if (avctx->sample_rate < 1 ||
67 avctx->sample_rate > INT_MAX / (avctx->channels * BLOCK_SIZE * 8))
68 return AVERROR_INVALIDDATA;
69
70 /* bit rate */
71 avctx->bit_rate = avctx->sample_rate * avctx->channels * BLOCK_SIZE * 8 / BLOCK_SAMPLES;
72
73 /* LPC coefficients */
74 if (coeff) {
75 cutoff = AV_RB16(buf + 16);
76 ff_adx_calculate_coeffs(cutoff, avctx->sample_rate, COEFF_BITS, coeff);
77 }
78
79 *header_size = offset;
80 return 0;
81}
libavcodec/adx.h+21−0
@@ -31,6 +31,10 @@ · 30 unmodified lines
31#ifndef AVCODEC_ADX_H31#ifndef AVCODEC_ADX_H
32#define AVCODEC_ADX_H32#define AVCODEC_ADX_H
33 33
34#include <stdint.h>
35
36#include "avcodec.h"
37
34typedef struct {38typedef struct {
35 int s1,s2;39 int s1,s2;
36} ADXChannelState;40} ADXChannelState;
@@ -47,6 +51,9 @@ typedef struct { · 10 unmodified lines
47 51
48#define COEFF_BITS 1252#define COEFF_BITS 12
49 53
54#define BLOCK_SIZE 18
55#define BLOCK_SAMPLES 32
56
50/**57/**
51 * Calculate LPC coefficients based on cutoff frequency and sample rate.58 * Calculate LPC coefficients based on cutoff frequency and sample rate.
52 *59 *
@@ -57,4 +64,18 @@ typedef struct { · 4 unmodified lines
57 */64 */
58void ff_adx_calculate_coeffs(int cutoff, int sample_rate, int bits, int *coeff);65void ff_adx_calculate_coeffs(int cutoff, int sample_rate, int bits, int *coeff);
59 66
67/**
68 * Decode ADX stream header.
69 * Sets avctx->channels and avctx->sample_rate.
70 *
71 * @param avctx codec context
72 * @param buf header data
73 * @param bufsize data size, should be at least 24 bytes
74 * @param[out] header_size size of ADX header
75 * @param[out] coeff 2 LPC coefficients, can be NULL
76 * @return data offset or negative error code if header is invalid
77 */
78int ff_adx_decode_header(AVCodecContext *avctx, const uint8_t *buf, int bufsize,
79 int *header_size, int *coeff);
80
60#endif /* AVCODEC_ADX_H */81#endif /* AVCODEC_ADX_H */
libavcodec/adxdec.c+6−36
@@ -33,9 +33,6 @@ · 32 unmodified lines
33 * adx2wav & wav2adx http://www.geocities.co.jp/Playtown/2004/33 * adx2wav & wav2adx http://www.geocities.co.jp/Playtown/2004/
34 */34 */
35 35
36#define BLOCK_SIZE 18
37#define BLOCK_SAMPLES 32
38
39static av_cold int adx_decode_init(AVCodecContext *avctx)36static av_cold int adx_decode_init(AVCodecContext *avctx)
40{37{
41 avctx->sample_fmt = AV_SAMPLE_FMT_S16;38 avctx->sample_fmt = AV_SAMPLE_FMT_S16;
@@ -72,45 +69,18 @@ static void adx_decode(ADXContext *c, int16_t *out, const uint8_t *in, int ch) · 30 unmodified lines
72 prev->s2 = s2;69 prev->s2 = s2;
73}70}
74 71
75/**
76 * Decode stream header.
77 *
78 * @param avctx codec context
79 * @param buf packet data
80 * @param bufsize packet size
81 * @return data offset or negative error code if header is invalid
82 */
83static int adx_decode_header(AVCodecContext *avctx, const uint8_t *buf,72static int adx_decode_header(AVCodecContext *avctx, const uint8_t *buf,
84 int bufsize)73 int bufsize)
85{74{
86 ADXContext *c = avctx->priv_data;75 ADXContext *c = avctx->priv_data;
87 int offset, cutoff;76 int ret, header_size;
88
89 if (AV_RB16(buf) != 0x8000)
90 return AVERROR_INVALIDDATA;
91 offset = AV_RB16(buf + 2) + 4;
92 if (bufsize < offset || memcmp(buf + offset - 6, "(c)CRI", 6))
93 return AVERROR_INVALIDDATA;
94
95 /* check for encoding=3 block_size=18, sample_size=4 */
96 if (buf[4] != 3 || buf[5] != 18 || buf[6] != 4) {
97 av_log_ask_for_sample(avctx, "unsupported ADX format\n");
98 return AVERROR_PATCHWELCOME;
99 }
100
101 c->channels = avctx->channels = buf[7];
102 if (avctx->channels > 2)
103 return AVERROR_INVALIDDATA;
104 avctx->sample_rate = AV_RB32(buf + 8);
105 if (avctx->sample_rate < 1 ||
106 avctx->sample_rate > INT_MAX / (avctx->channels * BLOCK_SIZE * 8))
107 return AVERROR_INVALIDDATA;
108 avctx->bit_rate = avctx->sample_rate * avctx->channels * BLOCK_SIZE * 8 / BLOCK_SAMPLES;
109 77
110 cutoff = AV_RB16(buf + 16);78 if ((ret = ff_adx_decode_header(avctx, buf, bufsize, &header_size,
111 ff_adx_calculate_coeffs(cutoff, avctx->sample_rate, COEFF_BITS, c->coeff);79 c->coeff)) < 0)
80 return ret;
112 81
113 return offset;82 c->channels = avctx->channels;
83 return header_size;
114}84}
115 85
116static int adx_decode_frame(AVCodecContext *avctx, void *data, int *data_size,86static int adx_decode_frame(AVCodecContext *avctx, void *data, int *data_size,

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t