pcm.c 18.6 KB
Newer Older
Fabrice Bellard's avatar
Fabrice Bellard committed
1 2
/*
 * PCM codecs
3
 * Copyright (c) 2001 Fabrice Bellard
Fabrice Bellard's avatar
Fabrice Bellard committed
4
 *
5 6 7
 * This file is part of FFmpeg.
 *
 * FFmpeg is free software; you can redistribute it and/or
8 9
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
10
 * version 2.1 of the License, or (at your option) any later version.
Fabrice Bellard's avatar
Fabrice Bellard committed
11
 *
12
 * FFmpeg is distributed in the hope that it will be useful,
Fabrice Bellard's avatar
Fabrice Bellard committed
13
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 15
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
Fabrice Bellard's avatar
Fabrice Bellard committed
16
 *
17
 * You should have received a copy of the GNU Lesser General Public
18
 * License along with FFmpeg; if not, write to the Free Software
19
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
Fabrice Bellard's avatar
Fabrice Bellard committed
20
 */
21

Michael Niedermayer's avatar
Michael Niedermayer committed
22
/**
23
 * @file libavcodec/pcm.c
Michael Niedermayer's avatar
Michael Niedermayer committed
24 25
 * PCM codecs
 */
26

Fabrice Bellard's avatar
Fabrice Bellard committed
27
#include "avcodec.h"
28
#include "libavutil/common.h" /* for av_reverse */
Ramiro Polla's avatar
Ramiro Polla committed
29
#include "bytestream.h"
Fabrice Bellard's avatar
Fabrice Bellard committed
30

31 32
#define MAX_CHANNELS 64

Fabrice Bellard's avatar
Fabrice Bellard committed
33 34
/* from g711.c by SUN microsystems (unrestricted use) */

35 36 37 38 39
#define         SIGN_BIT        (0x80)      /* Sign bit for a A-law byte. */
#define         QUANT_MASK      (0xf)       /* Quantization field mask. */
#define         NSEGS           (8)         /* Number of A-law segments. */
#define         SEG_SHIFT       (4)         /* Left shift for segment number. */
#define         SEG_MASK        (0x70)      /* Segment field mask. */
Fabrice Bellard's avatar
Fabrice Bellard committed
40

41
#define         BIAS            (0x84)      /* Bias for linear code. */
Fabrice Bellard's avatar
Fabrice Bellard committed
42 43 44 45 46

/*
 * alaw2linear() - Convert an A-law value to 16-bit linear PCM
 *
 */
47
static av_cold int alaw2linear(unsigned char a_val)
Fabrice Bellard's avatar
Fabrice Bellard committed
48
{
49 50
        int t;
        int seg;
Fabrice Bellard's avatar
Fabrice Bellard committed
51

52
        a_val ^= 0x55;
Fabrice Bellard's avatar
Fabrice Bellard committed
53

54 55 56 57
        t = a_val & QUANT_MASK;
        seg = ((unsigned)a_val & SEG_MASK) >> SEG_SHIFT;
        if(seg) t= (t + t + 1 + 32) << (seg + 2);
        else    t= (t + t + 1     ) << 3;
Michael Niedermayer's avatar
Michael Niedermayer committed
58

59
        return (a_val & SIGN_BIT) ? t : -t;
Fabrice Bellard's avatar
Fabrice Bellard committed
60 61
}

62
static av_cold int ulaw2linear(unsigned char u_val)
Fabrice Bellard's avatar
Fabrice Bellard committed
63
{
64
        int t;
Fabrice Bellard's avatar
Fabrice Bellard committed
65

66 67
        /* Complement to obtain normal u-law value. */
        u_val = ~u_val;
Fabrice Bellard's avatar
Fabrice Bellard committed
68

69 70 71 72 73 74
        /*
         * Extract and bias the quantization bits. Then
         * shift up by the segment number and subtract out the bias.
         */
        t = ((u_val & QUANT_MASK) << 3) + BIAS;
        t <<= ((unsigned)u_val & SEG_MASK) >> SEG_SHIFT;
Fabrice Bellard's avatar
Fabrice Bellard committed
75

76
        return (u_val & SIGN_BIT) ? (BIAS - t) : (t - BIAS);
Fabrice Bellard's avatar
Fabrice Bellard committed
77 78 79
}

/* 16384 entries per table */
80 81
static uint8_t linear_to_alaw[16384];
static uint8_t linear_to_ulaw[16384];
Fabrice Bellard's avatar
Fabrice Bellard committed
82

83
static av_cold void build_xlaw_table(uint8_t *linear_to_xlaw,
Fabrice Bellard's avatar
Fabrice Bellard committed
84
                             int (*xlaw2linear)(unsigned char),
85
                             int mask)
Fabrice Bellard's avatar
Fabrice Bellard committed
86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106
{
    int i, j, v, v1, v2;

    j = 0;
    for(i=0;i<128;i++) {
        if (i != 127) {
            v1 = xlaw2linear(i ^ mask);
            v2 = xlaw2linear((i + 1) ^ mask);
            v = (v1 + v2 + 4) >> 3;
        } else {
            v = 8192;
        }
        for(;j<v;j++) {
            linear_to_xlaw[8192 + j] = (i ^ mask);
            if (j > 0)
                linear_to_xlaw[8192 - j] = (i ^ (mask ^ 0x80));
        }
    }
    linear_to_xlaw[0] = linear_to_xlaw[1];
}

107
static av_cold int pcm_encode_init(AVCodecContext *avctx)
Fabrice Bellard's avatar
Fabrice Bellard committed
108 109 110 111
{
    avctx->frame_size = 1;
    switch(avctx->codec->id) {
    case CODEC_ID_PCM_ALAW:
112
        build_xlaw_table(linear_to_alaw, alaw2linear, 0xd5);
Fabrice Bellard's avatar
Fabrice Bellard committed
113 114
        break;
    case CODEC_ID_PCM_MULAW:
115
        build_xlaw_table(linear_to_ulaw, ulaw2linear, 0xff);
Fabrice Bellard's avatar
Fabrice Bellard committed
116 117 118 119
        break;
    default:
        break;
    }
120

121 122
    avctx->bits_per_coded_sample = av_get_bits_per_sample(avctx->codec->id);
    avctx->block_align = avctx->channels * avctx->bits_per_coded_sample/8;
123 124
    avctx->coded_frame= avcodec_alloc_frame();
    avctx->coded_frame->key_frame= 1;
125

Fabrice Bellard's avatar
Fabrice Bellard committed
126 127 128
    return 0;
}

129
static av_cold int pcm_encode_close(AVCodecContext *avctx)
Fabrice Bellard's avatar
Fabrice Bellard committed
130
{
131 132
    av_freep(&avctx->coded_frame);

Fabrice Bellard's avatar
Fabrice Bellard committed
133 134 135
    return 0;
}

136 137 138 139 140 141 142
/**
 * Write PCM samples macro
 * @param type Datatype of native machine format
 * @param endian bytestream_put_xxx() suffix
 * @param src Source pointer (variable name)
 * @param dst Destination pointer (variable name)
 * @param n Total number of samples (variable name)
143
 * @param shift Bitshift (bits)
144 145
 * @param offset Sample value offset
 */
146 147
#define ENCODE(type, endian, src, dst, n, shift, offset) \
    samples_##type = (type*)src; \
148
    for(;n>0;n--) { \
149
        register type v = (*samples_##type++ >> shift) + offset; \
150
        bytestream_put_##endian(&dst, v); \
151
    }
152

153
static int pcm_encode_frame(AVCodecContext *avctx,
154
                            unsigned char *frame, int buf_size, void *data)
Fabrice Bellard's avatar
Fabrice Bellard committed
155 156 157 158
{
    int n, sample_size, v;
    short *samples;
    unsigned char *dst;
159 160 161
    uint8_t *srcu8;
    int16_t *samples_int16_t;
    int32_t *samples_int32_t;
162
    int64_t *samples_int64_t;
163 164
    uint16_t *samples_uint16_t;
    uint32_t *samples_uint32_t;
Fabrice Bellard's avatar
Fabrice Bellard committed
165

166
    sample_size = av_get_bits_per_sample(avctx->codec->id)/8;
Fabrice Bellard's avatar
Fabrice Bellard committed
167 168 169 170
    n = buf_size / sample_size;
    samples = data;
    dst = frame;

171 172 173 174 175
    if (avctx->sample_fmt!=avctx->codec->sample_fmts[0]) {
        av_log(avctx, AV_LOG_ERROR, "invalid sample_fmt\n");
        return -1;
    }

Fabrice Bellard's avatar
Fabrice Bellard committed
176
    switch(avctx->codec->id) {
177
    case CODEC_ID_PCM_U32LE:
178
        ENCODE(uint32_t, le32, samples, dst, n, 0, 0x80000000)
179 180
        break;
    case CODEC_ID_PCM_U32BE:
181
        ENCODE(uint32_t, be32, samples, dst, n, 0, 0x80000000)
182 183
        break;
    case CODEC_ID_PCM_S24LE:
184
        ENCODE(int32_t, le24, samples, dst, n, 8, 0)
185 186
        break;
    case CODEC_ID_PCM_S24BE:
187
        ENCODE(int32_t, be24, samples, dst, n, 8, 0)
188 189
        break;
    case CODEC_ID_PCM_U24LE:
190
        ENCODE(uint32_t, le24, samples, dst, n, 8, 0x800000)
191 192
        break;
    case CODEC_ID_PCM_U24BE:
193
        ENCODE(uint32_t, be24, samples, dst, n, 8, 0x800000)
194 195 196
        break;
    case CODEC_ID_PCM_S24DAUD:
        for(;n>0;n--) {
197 198
            uint32_t tmp = av_reverse[(*samples >> 8) & 0xff] +
                           (av_reverse[*samples & 0xff] << 8);
199
            tmp <<= 4; // sync flags would go here
Ramiro Polla's avatar
Ramiro Polla committed
200
            bytestream_put_be24(&dst, tmp);
201 202 203
            samples++;
        }
        break;
Fabrice Bellard's avatar
Fabrice Bellard committed
204
    case CODEC_ID_PCM_U16LE:
205
        ENCODE(uint16_t, le16, samples, dst, n, 0, 0x8000)
Fabrice Bellard's avatar
Fabrice Bellard committed
206 207
        break;
    case CODEC_ID_PCM_U16BE:
208
        ENCODE(uint16_t, be16, samples, dst, n, 0, 0x8000)
Fabrice Bellard's avatar
Fabrice Bellard committed
209 210
        break;
    case CODEC_ID_PCM_S8:
211
        srcu8= data;
Fabrice Bellard's avatar
Fabrice Bellard committed
212
        for(;n>0;n--) {
213 214
            v = *srcu8++;
            *dst++ = v - 128;
Fabrice Bellard's avatar
Fabrice Bellard committed
215 216
        }
        break;
217
#if HAVE_BIGENDIAN
218 219 220
    case CODEC_ID_PCM_F64LE:
        ENCODE(int64_t, le64, samples, dst, n, 0, 0)
        break;
221
    case CODEC_ID_PCM_S32LE:
222
    case CODEC_ID_PCM_F32LE:
223 224 225 226 227
        ENCODE(int32_t, le32, samples, dst, n, 0, 0)
        break;
    case CODEC_ID_PCM_S16LE:
        ENCODE(int16_t, le16, samples, dst, n, 0, 0)
        break;
228
    case CODEC_ID_PCM_F64BE:
229 230 231 232
    case CODEC_ID_PCM_F32BE:
    case CODEC_ID_PCM_S32BE:
    case CODEC_ID_PCM_S16BE:
#else
233 234 235
    case CODEC_ID_PCM_F64BE:
        ENCODE(int64_t, be64, samples, dst, n, 0, 0)
        break;
236 237 238 239 240 241 242
    case CODEC_ID_PCM_F32BE:
    case CODEC_ID_PCM_S32BE:
        ENCODE(int32_t, be32, samples, dst, n, 0, 0)
        break;
    case CODEC_ID_PCM_S16BE:
        ENCODE(int16_t, be16, samples, dst, n, 0, 0)
        break;
243 244
    case CODEC_ID_PCM_F64LE:
    case CODEC_ID_PCM_F32LE:
245 246
    case CODEC_ID_PCM_S32LE:
    case CODEC_ID_PCM_S16LE:
247
#endif /* HAVE_BIGENDIAN */
Fabrice Bellard's avatar
Fabrice Bellard committed
248
    case CODEC_ID_PCM_U8:
249 250
        memcpy(dst, samples, n*sample_size);
        dst += n*sample_size;
Fabrice Bellard's avatar
Fabrice Bellard committed
251
        break;
252 253 254 255 256 257 258 259
    case CODEC_ID_PCM_ZORK:
        for(;n>0;n--) {
            v= *samples++ >> 8;
            if(v<0)   v = -v;
            else      v+= 128;
            *dst++ = v;
        }
        break;
Fabrice Bellard's avatar
Fabrice Bellard committed
260 261 262
    case CODEC_ID_PCM_ALAW:
        for(;n>0;n--) {
            v = *samples++;
263
            *dst++ = linear_to_alaw[(v + 32768) >> 2];
Fabrice Bellard's avatar
Fabrice Bellard committed
264 265 266 267 268
        }
        break;
    case CODEC_ID_PCM_MULAW:
        for(;n>0;n--) {
            v = *samples++;
269
            *dst++ = linear_to_ulaw[(v + 32768) >> 2];
Fabrice Bellard's avatar
Fabrice Bellard committed
270 271 272 273 274
        }
        break;
    default:
        return -1;
    }
275
    //avctx->frame_size = (dst - frame) / (sample_size * avctx->channels);
276

Fabrice Bellard's avatar
Fabrice Bellard committed
277 278 279 280 281 282 283
    return dst - frame;
}

typedef struct PCMDecode {
    short table[256];
} PCMDecode;

284
static av_cold int pcm_decode_init(AVCodecContext * avctx)
Fabrice Bellard's avatar
Fabrice Bellard committed
285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300
{
    PCMDecode *s = avctx->priv_data;
    int i;

    switch(avctx->codec->id) {
    case CODEC_ID_PCM_ALAW:
        for(i=0;i<256;i++)
            s->table[i] = alaw2linear(i);
        break;
    case CODEC_ID_PCM_MULAW:
        for(i=0;i<256;i++)
            s->table[i] = ulaw2linear(i);
        break;
    default:
        break;
    }
301

302
    avctx->sample_fmt = avctx->codec->sample_fmts[0];
Fabrice Bellard's avatar
Fabrice Bellard committed
303 304 305
    return 0;
}

306 307 308 309 310 311 312
/**
 * Read PCM samples macro
 * @param type Datatype of native machine format
 * @param endian bytestream_get_xxx() endian suffix
 * @param src Source pointer (variable name)
 * @param dst Destination pointer (variable name)
 * @param n Total number of samples (variable name)
313
 * @param shift Bitshift (bits)
314 315
 * @param offset Sample value offset
 */
316 317
#define DECODE(type, endian, src, dst, n, shift, offset) \
    dst_##type = (type*)dst; \
318 319
    for(;n>0;n--) { \
        register type v = bytestream_get_##endian(&src); \
320
        *dst_##type++ = (v - offset) << shift; \
321
    } \
322
    dst = (short*)dst_##type;
323

324
static int pcm_decode_frame(AVCodecContext *avctx,
325
                            void *data, int *data_size,
326
                            AVPacket *avpkt)
Fabrice Bellard's avatar
Fabrice Bellard committed
327
{
328 329
    const uint8_t *buf = avpkt->data;
    int buf_size = avpkt->size;
Fabrice Bellard's avatar
Fabrice Bellard committed
330
    PCMDecode *s = avctx->priv_data;
331
    int sample_size, c, n;
Fabrice Bellard's avatar
Fabrice Bellard committed
332
    short *samples;
333
    const uint8_t *src, *src8, *src2[MAX_CHANNELS];
334 335 336
    uint8_t *dstu8;
    int16_t *dst_int16_t;
    int32_t *dst_int32_t;
337
    int64_t *dst_int64_t;
338 339
    uint16_t *dst_uint16_t;
    uint32_t *dst_uint32_t;
Fabrice Bellard's avatar
Fabrice Bellard committed
340 341 342 343

    samples = data;
    src = buf;

344 345 346 347 348
    if (avctx->sample_fmt!=avctx->codec->sample_fmts[0]) {
        av_log(avctx, AV_LOG_ERROR, "invalid sample_fmt\n");
        return -1;
    }

349 350 351 352
    if(avctx->channels <= 0 || avctx->channels > MAX_CHANNELS){
        av_log(avctx, AV_LOG_ERROR, "PCM channels out of bounds\n");
        return -1;
    }
353

354 355
    sample_size = av_get_bits_per_sample(avctx->codec_id)/8;

356 357 358
    /* av_get_bits_per_sample returns 0 for CODEC_ID_PCM_DVD */
    if (CODEC_ID_PCM_DVD == avctx->codec_id)
        /* 2 samples are interleaved per block in PCM_DVD */
359
        sample_size = avctx->bits_per_coded_sample * 2 / 8;
360 361

    n = avctx->channels * sample_size;
362 363

    if(n && buf_size % n){
364
        if (buf_size < n) {
Michael Niedermayer's avatar
Michael Niedermayer committed
365 366
            av_log(avctx, AV_LOG_ERROR, "invalid PCM packet\n");
            return -1;
367 368
        }else
            buf_size -= buf_size % n;
369 370
    }

371 372
    buf_size= FFMIN(buf_size, *data_size/2);
    *data_size=0;
Michael Niedermayer's avatar
Michael Niedermayer committed
373

374
    n = buf_size/sample_size;
375

Fabrice Bellard's avatar
Fabrice Bellard committed
376
    switch(avctx->codec->id) {
377
    case CODEC_ID_PCM_U32LE:
378
        DECODE(uint32_t, le32, src, samples, n, 0, 0x80000000)
379 380
        break;
    case CODEC_ID_PCM_U32BE:
381
        DECODE(uint32_t, be32, src, samples, n, 0, 0x80000000)
382 383
        break;
    case CODEC_ID_PCM_S24LE:
384
        DECODE(int32_t, le24, src, samples, n, 8, 0)
385 386
        break;
    case CODEC_ID_PCM_S24BE:
387
        DECODE(int32_t, be24, src, samples, n, 8, 0)
388 389
        break;
    case CODEC_ID_PCM_U24LE:
390
        DECODE(uint32_t, le24, src, samples, n, 8, 0x800000)
391 392
        break;
    case CODEC_ID_PCM_U24BE:
393
        DECODE(uint32_t, be24, src, samples, n, 8, 0x800000)
394 395 396
        break;
    case CODEC_ID_PCM_S24DAUD:
        for(;n>0;n--) {
Ramiro Polla's avatar
Ramiro Polla committed
397
          uint32_t v = bytestream_get_be24(&src);
398
          v >>= 4; // sync flags are here
399 400
          *samples++ = av_reverse[(v >> 8) & 0xff] +
                       (av_reverse[v & 0xff] << 8);
401 402
        }
        break;
403
    case CODEC_ID_PCM_S16LE_PLANAR:
404 405
        n /= avctx->channels;
        for(c=0;c<avctx->channels;c++)
406 407
            src2[c] = &src[c*n*2];
        for(;n>0;n--)
408 409 410 411
            for(c=0;c<avctx->channels;c++)
                *samples++ = bytestream_get_le16(&src2[c]);
        src = src2[avctx->channels-1];
        break;
Fabrice Bellard's avatar
Fabrice Bellard committed
412
    case CODEC_ID_PCM_U16LE:
413
        DECODE(uint16_t, le16, src, samples, n, 0, 0x8000)
Fabrice Bellard's avatar
Fabrice Bellard committed
414 415
        break;
    case CODEC_ID_PCM_U16BE:
416
        DECODE(uint16_t, be16, src, samples, n, 0, 0x8000)
Fabrice Bellard's avatar
Fabrice Bellard committed
417 418
        break;
    case CODEC_ID_PCM_S8:
419
        dstu8= (uint8_t*)samples;
Fabrice Bellard's avatar
Fabrice Bellard committed
420
        for(;n>0;n--) {
421
            *dstu8++ = *src++ + 128;
Fabrice Bellard's avatar
Fabrice Bellard committed
422
        }
423
        samples= (short*)dstu8;
Fabrice Bellard's avatar
Fabrice Bellard committed
424
        break;
425
#if HAVE_BIGENDIAN
426 427 428
    case CODEC_ID_PCM_F64LE:
        DECODE(int64_t, le64, src, samples, n, 0, 0)
        break;
429
    case CODEC_ID_PCM_S32LE:
430
    case CODEC_ID_PCM_F32LE:
431 432 433 434 435
        DECODE(int32_t, le32, src, samples, n, 0, 0)
        break;
    case CODEC_ID_PCM_S16LE:
        DECODE(int16_t, le16, src, samples, n, 0, 0)
        break;
436
    case CODEC_ID_PCM_F64BE:
437 438 439 440
    case CODEC_ID_PCM_F32BE:
    case CODEC_ID_PCM_S32BE:
    case CODEC_ID_PCM_S16BE:
#else
441 442 443
    case CODEC_ID_PCM_F64BE:
        DECODE(int64_t, be64, src, samples, n, 0, 0)
        break;
444 445 446 447 448 449 450
    case CODEC_ID_PCM_F32BE:
    case CODEC_ID_PCM_S32BE:
        DECODE(int32_t, be32, src, samples, n, 0, 0)
        break;
    case CODEC_ID_PCM_S16BE:
        DECODE(int16_t, be16, src, samples, n, 0, 0)
        break;
451 452
    case CODEC_ID_PCM_F64LE:
    case CODEC_ID_PCM_F32LE:
453 454
    case CODEC_ID_PCM_S32LE:
    case CODEC_ID_PCM_S16LE:
455
#endif /* HAVE_BIGENDIAN */
Fabrice Bellard's avatar
Fabrice Bellard committed
456
    case CODEC_ID_PCM_U8:
457 458 459
        memcpy(samples, src, n*sample_size);
        src += n*sample_size;
        samples = (short*)((uint8_t*)data + n*sample_size);
Fabrice Bellard's avatar
Fabrice Bellard committed
460
        break;
461 462 463 464 465 466 467 468
    case CODEC_ID_PCM_ZORK:
        for(;n>0;n--) {
            int x= *src++;
            if(x&128) x-= 128;
            else      x = -x;
            *samples++ = x << 8;
        }
        break;
Fabrice Bellard's avatar
Fabrice Bellard committed
469 470 471
    case CODEC_ID_PCM_ALAW:
    case CODEC_ID_PCM_MULAW:
        for(;n>0;n--) {
472
            *samples++ = s->table[*src++];
Fabrice Bellard's avatar
Fabrice Bellard committed
473 474
        }
        break;
475
    case CODEC_ID_PCM_DVD:
476 477
        dst_int32_t = data;
        n /= avctx->channels;
478
        switch (avctx->bits_per_coded_sample) {
479
        case 20:
480
            while (n--) {
481 482 483 484 485 486 487
                c = avctx->channels;
                src8 = src + 4*c;
                while (c--) {
                    *dst_int32_t++ = (bytestream_get_be16(&src) << 16) + ((*src8   &0xf0) << 8);
                    *dst_int32_t++ = (bytestream_get_be16(&src) << 16) + ((*src8++ &0x0f) << 12);
                }
                src = src8;
488
            }
489 490 491 492 493 494 495 496 497 498 499 500 501 502 503 504
            break;
        case 24:
            while (n--) {
                c = avctx->channels;
                src8 = src + 4*c;
                while (c--) {
                    *dst_int32_t++ = (bytestream_get_be16(&src) << 16) + ((*src8++) << 8);
                    *dst_int32_t++ = (bytestream_get_be16(&src) << 16) + ((*src8++) << 8);
                }
                src = src8;
            }
            break;
        default:
            av_log(avctx, AV_LOG_ERROR, "PCM DVD unsupported sample depth\n");
            return -1;
            break;
505
        }
506
        samples = (short *) dst_int32_t;
507
        break;
Fabrice Bellard's avatar
Fabrice Bellard committed
508 509 510
    default:
        return -1;
    }
511
    *data_size = (uint8_t *)samples - (uint8_t *)data;
Fabrice Bellard's avatar
Fabrice Bellard committed
512 513 514
    return src - buf;
}

515
#if CONFIG_ENCODERS
516
#define PCM_ENCODER(id,sample_fmt_,name,long_name_) \
Fabrice Bellard's avatar
Fabrice Bellard committed
517 518 519 520 521
AVCodec name ## _encoder = {                    \
    #name,                                      \
    CODEC_TYPE_AUDIO,                           \
    id,                                         \
    0,                                          \
522 523 524
    pcm_encode_init,                            \
    pcm_encode_frame,                           \
    pcm_encode_close,                           \
Fabrice Bellard's avatar
Fabrice Bellard committed
525
    NULL,                                       \
526
    .sample_fmts = (const enum SampleFormat[]){sample_fmt_,SAMPLE_FMT_NONE}, \
527
    .long_name = NULL_IF_CONFIG_SMALL(long_name_), \
528 529
};
#else
530
#define PCM_ENCODER(id,sample_fmt_,name,long_name_)
531 532
#endif

533
#if CONFIG_DECODERS
534
#define PCM_DECODER(id,sample_fmt_,name,long_name_)         \
Fabrice Bellard's avatar
Fabrice Bellard committed
535 536 537 538 539
AVCodec name ## _decoder = {                    \
    #name,                                      \
    CODEC_TYPE_AUDIO,                           \
    id,                                         \
    sizeof(PCMDecode),                          \
540
    pcm_decode_init,                            \
Fabrice Bellard's avatar
Fabrice Bellard committed
541 542
    NULL,                                       \
    NULL,                                       \
543
    pcm_decode_frame,                           \
544
    .sample_fmts = (const enum SampleFormat[]){sample_fmt_,SAMPLE_FMT_NONE}, \
545
    .long_name = NULL_IF_CONFIG_SMALL(long_name_), \
546 547
};
#else
548
#define PCM_DECODER(id,sample_fmt_,name,long_name_)
549 550
#endif

551
#define PCM_CODEC(id, sample_fmt_, name, long_name_)         \
552
    PCM_ENCODER(id,sample_fmt_,name,long_name_) PCM_DECODER(id,sample_fmt_,name,long_name_)
553

554
/* Note: Do not forget to add new entries to the Makefile as well. */
555 556 557 558 559 560 561 562 563 564 565 566 567 568 569 570 571 572 573 574 575 576 577 578
PCM_CODEC  (CODEC_ID_PCM_ALAW,  SAMPLE_FMT_S16, pcm_alaw, "PCM A-law");
PCM_CODEC  (CODEC_ID_PCM_DVD,   SAMPLE_FMT_S32, pcm_dvd, "PCM signed 20|24-bit big-endian");
PCM_CODEC  (CODEC_ID_PCM_F32BE, SAMPLE_FMT_FLT, pcm_f32be, "PCM 32-bit floating point big-endian");
PCM_CODEC  (CODEC_ID_PCM_F32LE, SAMPLE_FMT_FLT, pcm_f32le, "PCM 32-bit floating point little-endian");
PCM_CODEC  (CODEC_ID_PCM_F64BE, SAMPLE_FMT_DBL, pcm_f64be, "PCM 64-bit floating point big-endian");
PCM_CODEC  (CODEC_ID_PCM_F64LE, SAMPLE_FMT_DBL, pcm_f64le, "PCM 64-bit floating point little-endian");
PCM_CODEC  (CODEC_ID_PCM_MULAW, SAMPLE_FMT_S16, pcm_mulaw, "PCM mu-law");
PCM_CODEC  (CODEC_ID_PCM_S8,    SAMPLE_FMT_U8,  pcm_s8, "PCM signed 8-bit");
PCM_CODEC  (CODEC_ID_PCM_S16BE, SAMPLE_FMT_S16, pcm_s16be, "PCM signed 16-bit big-endian");
PCM_CODEC  (CODEC_ID_PCM_S16LE, SAMPLE_FMT_S16, pcm_s16le, "PCM signed 16-bit little-endian");
PCM_DECODER(CODEC_ID_PCM_S16LE_PLANAR, SAMPLE_FMT_S16, pcm_s16le_planar, "PCM 16-bit little-endian planar");
PCM_CODEC  (CODEC_ID_PCM_S24BE, SAMPLE_FMT_S32, pcm_s24be, "PCM signed 24-bit big-endian");
PCM_CODEC  (CODEC_ID_PCM_S24DAUD, SAMPLE_FMT_S16,  pcm_s24daud, "PCM D-Cinema audio signed 24-bit");
PCM_CODEC  (CODEC_ID_PCM_S24LE, SAMPLE_FMT_S32, pcm_s24le, "PCM signed 24-bit little-endian");
PCM_CODEC  (CODEC_ID_PCM_S32BE, SAMPLE_FMT_S32, pcm_s32be, "PCM signed 32-bit big-endian");
PCM_CODEC  (CODEC_ID_PCM_S32LE, SAMPLE_FMT_S32, pcm_s32le, "PCM signed 32-bit little-endian");
PCM_CODEC  (CODEC_ID_PCM_U8,    SAMPLE_FMT_U8,  pcm_u8, "PCM unsigned 8-bit");
PCM_CODEC  (CODEC_ID_PCM_U16BE, SAMPLE_FMT_S16, pcm_u16be, "PCM unsigned 16-bit big-endian");
PCM_CODEC  (CODEC_ID_PCM_U16LE, SAMPLE_FMT_S16, pcm_u16le, "PCM unsigned 16-bit little-endian");
PCM_CODEC  (CODEC_ID_PCM_U24BE, SAMPLE_FMT_S32, pcm_u24be, "PCM unsigned 24-bit big-endian");
PCM_CODEC  (CODEC_ID_PCM_U24LE, SAMPLE_FMT_S32, pcm_u24le, "PCM unsigned 24-bit little-endian");
PCM_CODEC  (CODEC_ID_PCM_U32BE, SAMPLE_FMT_S32, pcm_u32be, "PCM unsigned 32-bit big-endian");
PCM_CODEC  (CODEC_ID_PCM_U32LE, SAMPLE_FMT_S32, pcm_u32le, "PCM unsigned 32-bit little-endian");
PCM_CODEC  (CODEC_ID_PCM_ZORK,  SAMPLE_FMT_S16, pcm_zork, "PCM Zork");