libavcodec/dpcm.c
Go to the documentation of this file.
00001 /*
00002  * Assorted DPCM codecs
00003  * Copyright (c) 2003 The ffmpeg Project
00004  *
00005  * This file is part of FFmpeg.
00006  *
00007  * FFmpeg is free software; you can redistribute it and/or
00008  * modify it under the terms of the GNU Lesser General Public
00009  * License as published by the Free Software Foundation; either
00010  * version 2.1 of the License, or (at your option) any later version.
00011  *
00012  * FFmpeg is distributed in the hope that it will be useful,
00013  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00014  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00015  * Lesser General Public License for more details.
00016  *
00017  * You should have received a copy of the GNU Lesser General Public
00018  * License along with FFmpeg; if not, write to the Free Software
00019  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
00020  */
00021 
00040 #include "libavutil/intreadwrite.h"
00041 #include "avcodec.h"
00042 #include "bytestream.h"
00043 
00044 typedef struct DPCMContext {
00045     AVFrame frame;
00046     int channels;
00047     int16_t roq_square_array[256];
00048     int sample[2];                  
00049     const int8_t *sol_table;        
00050 } DPCMContext;
00051 
00052 static const int16_t interplay_delta_table[] = {
00053          0,      1,      2,      3,      4,      5,      6,      7,
00054          8,      9,     10,     11,     12,     13,     14,     15,
00055         16,     17,     18,     19,     20,     21,     22,     23,
00056         24,     25,     26,     27,     28,     29,     30,     31,
00057         32,     33,     34,     35,     36,     37,     38,     39,
00058         40,     41,     42,     43,     47,     51,     56,     61,
00059         66,     72,     79,     86,     94,    102,    112,    122,
00060        133,    145,    158,    173,    189,    206,    225,    245,
00061        267,    292,    318,    348,    379,    414,    452,    493,
00062        538,    587,    640,    699,    763,    832,    908,    991,
00063       1081,   1180,   1288,   1405,   1534,   1673,   1826,   1993,
00064       2175,   2373,   2590,   2826,   3084,   3365,   3672,   4008,
00065       4373,   4772,   5208,   5683,   6202,   6767,   7385,   8059,
00066       8794,   9597,  10472,  11428,  12471,  13609,  14851,  16206,
00067      17685,  19298,  21060,  22981,  25078,  27367,  29864,  32589,
00068     -29973, -26728, -23186, -19322, -15105, -10503,  -5481,     -1,
00069          1,      1,   5481,  10503,  15105,  19322,  23186,  26728,
00070      29973, -32589, -29864, -27367, -25078, -22981, -21060, -19298,
00071     -17685, -16206, -14851, -13609, -12471, -11428, -10472,  -9597,
00072      -8794,  -8059,  -7385,  -6767,  -6202,  -5683,  -5208,  -4772,
00073      -4373,  -4008,  -3672,  -3365,  -3084,  -2826,  -2590,  -2373,
00074      -2175,  -1993,  -1826,  -1673,  -1534,  -1405,  -1288,  -1180,
00075      -1081,   -991,   -908,   -832,   -763,   -699,   -640,   -587,
00076       -538,   -493,   -452,   -414,   -379,   -348,   -318,   -292,
00077       -267,   -245,   -225,   -206,   -189,   -173,   -158,   -145,
00078       -133,   -122,   -112,   -102,    -94,    -86,    -79,    -72,
00079        -66,    -61,    -56,    -51,    -47,    -43,    -42,    -41,
00080        -40,    -39,    -38,    -37,    -36,    -35,    -34,    -33,
00081        -32,    -31,    -30,    -29,    -28,    -27,    -26,    -25,
00082        -24,    -23,    -22,    -21,    -20,    -19,    -18,    -17,
00083        -16,    -15,    -14,    -13,    -12,    -11,    -10,     -9,
00084         -8,     -7,     -6,     -5,     -4,     -3,     -2,     -1
00085 
00086 };
00087 
00088 static const int8_t sol_table_old[16] = {
00089       0x0,  0x1,  0x2,  0x3,  0x6,  0xA,  0xF, 0x15,
00090     -0x15, -0xF, -0xA, -0x6, -0x3, -0x2, -0x1,  0x0
00091 };
00092 
00093 static const int8_t sol_table_new[16] = {
00094     0x0,  0x1,  0x2,  0x3,  0x6,  0xA,  0xF,  0x15,
00095     0x0, -0x1, -0x2, -0x3, -0x6, -0xA, -0xF, -0x15
00096 };
00097 
00098 static const int16_t sol_table_16[128] = {
00099     0x000, 0x008, 0x010, 0x020, 0x030, 0x040, 0x050, 0x060, 0x070, 0x080,
00100     0x090, 0x0A0, 0x0B0, 0x0C0, 0x0D0, 0x0E0, 0x0F0, 0x100, 0x110, 0x120,
00101     0x130, 0x140, 0x150, 0x160, 0x170, 0x180, 0x190, 0x1A0, 0x1B0, 0x1C0,
00102     0x1D0, 0x1E0, 0x1F0, 0x200, 0x208, 0x210, 0x218, 0x220, 0x228, 0x230,
00103     0x238, 0x240, 0x248, 0x250, 0x258, 0x260, 0x268, 0x270, 0x278, 0x280,
00104     0x288, 0x290, 0x298, 0x2A0, 0x2A8, 0x2B0, 0x2B8, 0x2C0, 0x2C8, 0x2D0,
00105     0x2D8, 0x2E0, 0x2E8, 0x2F0, 0x2F8, 0x300, 0x308, 0x310, 0x318, 0x320,
00106     0x328, 0x330, 0x338, 0x340, 0x348, 0x350, 0x358, 0x360, 0x368, 0x370,
00107     0x378, 0x380, 0x388, 0x390, 0x398, 0x3A0, 0x3A8, 0x3B0, 0x3B8, 0x3C0,
00108     0x3C8, 0x3D0, 0x3D8, 0x3E0, 0x3E8, 0x3F0, 0x3F8, 0x400, 0x440, 0x480,
00109     0x4C0, 0x500, 0x540, 0x580, 0x5C0, 0x600, 0x640, 0x680, 0x6C0, 0x700,
00110     0x740, 0x780, 0x7C0, 0x800, 0x900, 0xA00, 0xB00, 0xC00, 0xD00, 0xE00,
00111     0xF00, 0x1000, 0x1400, 0x1800, 0x1C00, 0x2000, 0x3000, 0x4000
00112 };
00113 
00114 
00115 static av_cold int dpcm_decode_init(AVCodecContext *avctx)
00116 {
00117     DPCMContext *s = avctx->priv_data;
00118     int i;
00119 
00120     if (avctx->channels < 1 || avctx->channels > 2) {
00121         av_log(avctx, AV_LOG_INFO, "invalid number of channels\n");
00122         return AVERROR(EINVAL);
00123     }
00124 
00125     s->channels = avctx->channels;
00126     s->sample[0] = s->sample[1] = 0;
00127 
00128     switch(avctx->codec->id) {
00129 
00130     case CODEC_ID_ROQ_DPCM:
00131         /* initialize square table */
00132         for (i = 0; i < 128; i++) {
00133             int16_t square = i * i;
00134             s->roq_square_array[i      ] =  square;
00135             s->roq_square_array[i + 128] = -square;
00136         }
00137         break;
00138 
00139     case CODEC_ID_SOL_DPCM:
00140         switch(avctx->codec_tag){
00141         case 1:
00142             s->sol_table = sol_table_old;
00143             s->sample[0] = s->sample[1] = 0x80;
00144             break;
00145         case 2:
00146             s->sol_table = sol_table_new;
00147             s->sample[0] = s->sample[1] = 0x80;
00148             break;
00149         case 3:
00150             break;
00151         default:
00152             av_log(avctx, AV_LOG_ERROR, "Unknown SOL subcodec\n");
00153             return -1;
00154         }
00155         break;
00156 
00157     default:
00158         break;
00159     }
00160 
00161     if (avctx->codec->id == CODEC_ID_SOL_DPCM && avctx->codec_tag != 3)
00162         avctx->sample_fmt = AV_SAMPLE_FMT_U8;
00163     else
00164         avctx->sample_fmt = AV_SAMPLE_FMT_S16;
00165 
00166     avcodec_get_frame_defaults(&s->frame);
00167     avctx->coded_frame = &s->frame;
00168 
00169     return 0;
00170 }
00171 
00172 
00173 static int dpcm_decode_frame(AVCodecContext *avctx, void *data,
00174                              int *got_frame_ptr, AVPacket *avpkt)
00175 {
00176     const uint8_t *buf = avpkt->data;
00177     int buf_size = avpkt->size;
00178     const uint8_t *buf_end = buf + buf_size;
00179     DPCMContext *s = avctx->priv_data;
00180     int out = 0, ret;
00181     int predictor[2];
00182     int ch = 0;
00183     int stereo = s->channels - 1;
00184     int16_t *output_samples;
00185 
00186     if (stereo && (buf_size & 1)) {
00187         buf_size--;
00188         buf_end--;
00189     }
00190 
00191     /* calculate output size */
00192     switch(avctx->codec->id) {
00193     case CODEC_ID_ROQ_DPCM:
00194         out = buf_size - 8;
00195         break;
00196     case CODEC_ID_INTERPLAY_DPCM:
00197         out = buf_size - 6 - s->channels;
00198         break;
00199     case CODEC_ID_XAN_DPCM:
00200         out = buf_size - 2 * s->channels;
00201         break;
00202     case CODEC_ID_SOL_DPCM:
00203         if (avctx->codec_tag != 3)
00204             out = buf_size * 2;
00205         else
00206             out = buf_size;
00207         break;
00208     }
00209     if (out <= 0) {
00210         av_log(avctx, AV_LOG_ERROR, "packet is too small\n");
00211         return AVERROR(EINVAL);
00212     }
00213     if (out % s->channels) {
00214         av_log(avctx, AV_LOG_WARNING, "channels have differing number of samples\n");
00215     }
00216 
00217     /* get output buffer */
00218     s->frame.nb_samples = (out + s->channels - 1) / s->channels;
00219     if ((ret = avctx->get_buffer(avctx, &s->frame)) < 0) {
00220         av_log(avctx, AV_LOG_ERROR, "get_buffer() failed\n");
00221         return ret;
00222     }
00223     output_samples = (int16_t *)s->frame.data[0];
00224 
00225     switch(avctx->codec->id) {
00226 
00227     case CODEC_ID_ROQ_DPCM:
00228         buf += 6;
00229 
00230         if (stereo) {
00231             predictor[1] = (int16_t)(bytestream_get_byte(&buf) << 8);
00232             predictor[0] = (int16_t)(bytestream_get_byte(&buf) << 8);
00233         } else {
00234             predictor[0] = (int16_t)bytestream_get_le16(&buf);
00235         }
00236 
00237         /* decode the samples */
00238         while (buf < buf_end) {
00239             predictor[ch] += s->roq_square_array[*buf++];
00240             predictor[ch]  = av_clip_int16(predictor[ch]);
00241             *output_samples++ = predictor[ch];
00242 
00243             /* toggle channel */
00244             ch ^= stereo;
00245         }
00246         break;
00247 
00248     case CODEC_ID_INTERPLAY_DPCM:
00249         buf += 6;  /* skip over the stream mask and stream length */
00250 
00251         for (ch = 0; ch < s->channels; ch++) {
00252             predictor[ch] = (int16_t)bytestream_get_le16(&buf);
00253             *output_samples++ = predictor[ch];
00254         }
00255 
00256         ch = 0;
00257         while (buf < buf_end) {
00258             predictor[ch] += interplay_delta_table[*buf++];
00259             predictor[ch]  = av_clip_int16(predictor[ch]);
00260             *output_samples++ = predictor[ch];
00261 
00262             /* toggle channel */
00263             ch ^= stereo;
00264         }
00265         break;
00266 
00267     case CODEC_ID_XAN_DPCM:
00268     {
00269         int shift[2] = { 4, 4 };
00270 
00271         for (ch = 0; ch < s->channels; ch++)
00272             predictor[ch] = (int16_t)bytestream_get_le16(&buf);
00273 
00274         ch = 0;
00275         while (buf < buf_end) {
00276             uint8_t n = *buf++;
00277             int16_t diff = (n & 0xFC) << 8;
00278             if ((n & 0x03) == 3)
00279                 shift[ch]++;
00280             else
00281                 shift[ch] -= (2 * (n & 3));
00282             /* saturate the shifter to a lower limit of 0 */
00283             if (shift[ch] < 0)
00284                 shift[ch] = 0;
00285 
00286             diff >>= shift[ch];
00287             predictor[ch] += diff;
00288 
00289             predictor[ch] = av_clip_int16(predictor[ch]);
00290             *output_samples++ = predictor[ch];
00291 
00292             /* toggle channel */
00293             ch ^= stereo;
00294         }
00295         break;
00296     }
00297     case CODEC_ID_SOL_DPCM:
00298         if (avctx->codec_tag != 3) {
00299             uint8_t *output_samples_u8 = s->frame.data[0];
00300             while (buf < buf_end) {
00301                 uint8_t n = *buf++;
00302 
00303                 s->sample[0] += s->sol_table[n >> 4];
00304                 s->sample[0]  = av_clip_uint8(s->sample[0]);
00305                 *output_samples_u8++ = s->sample[0];
00306 
00307                 s->sample[stereo] += s->sol_table[n & 0x0F];
00308                 s->sample[stereo]  = av_clip_uint8(s->sample[stereo]);
00309                 *output_samples_u8++ = s->sample[stereo];
00310             }
00311         } else {
00312             while (buf < buf_end) {
00313                 uint8_t n = *buf++;
00314                 if (n & 0x80) s->sample[ch] -= sol_table_16[n & 0x7F];
00315                 else          s->sample[ch] += sol_table_16[n & 0x7F];
00316                 s->sample[ch] = av_clip_int16(s->sample[ch]);
00317                 *output_samples++ = s->sample[ch];
00318                 /* toggle channel */
00319                 ch ^= stereo;
00320             }
00321         }
00322         break;
00323     }
00324 
00325     *got_frame_ptr   = 1;
00326     *(AVFrame *)data = s->frame;
00327 
00328     return avpkt->size;
00329 }
00330 
00331 #define DPCM_DECODER(id_, name_, long_name_)                \
00332 AVCodec ff_ ## name_ ## _decoder = {                        \
00333     .name           = #name_,                               \
00334     .type           = AVMEDIA_TYPE_AUDIO,                   \
00335     .id             = id_,                                  \
00336     .priv_data_size = sizeof(DPCMContext),                  \
00337     .init           = dpcm_decode_init,                     \
00338     .decode         = dpcm_decode_frame,                    \
00339     .capabilities   = CODEC_CAP_DR1,                        \
00340     .long_name      = NULL_IF_CONFIG_SMALL(long_name_),     \
00341 }
00342 
00343 DPCM_DECODER(CODEC_ID_INTERPLAY_DPCM, interplay_dpcm, "DPCM Interplay");
00344 DPCM_DECODER(CODEC_ID_ROQ_DPCM,       roq_dpcm,       "DPCM id RoQ");
00345 DPCM_DECODER(CODEC_ID_SOL_DPCM,       sol_dpcm,       "DPCM Sol");
00346 DPCM_DECODER(CODEC_ID_XAN_DPCM,       xan_dpcm,       "DPCM Xan");