• Main Page
  • Related Pages
  • Modules
  • Data Structures
  • Files
  • Examples
  • File List
  • Globals

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 
00043 typedef struct DPCMContext {
00044     int channels;
00045     short roq_square_array[256];
00046     long sample[2];//for SOL_DPCM
00047     const int *sol_table;//for SOL_DPCM
00048 } DPCMContext;
00049 
00050 #define SE_16BIT(x)  if (x & 0x8000) x -= 0x10000;
00051 
00052 static const int 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 int sol_table_old[16] =
00089     { 0x0,  0x1,  0x2 , 0x3,  0x6,  0xA,  0xF, 0x15,
00090     -0x15, -0xF, -0xA, -0x6, -0x3, -0x2, -0x1, 0x0};
00091 
00092 static const int sol_table_new[16] =
00093     { 0x0,  0x1,  0x2,  0x3,  0x6,  0xA,  0xF,  0x15,
00094       0x0, -0x1, -0x2, -0x3, -0x6, -0xA, -0xF, -0x15};
00095 
00096 static const int sol_table_16[128] = {
00097     0x000, 0x008, 0x010, 0x020, 0x030, 0x040, 0x050, 0x060, 0x070, 0x080,
00098     0x090, 0x0A0, 0x0B0, 0x0C0, 0x0D0, 0x0E0, 0x0F0, 0x100, 0x110, 0x120,
00099     0x130, 0x140, 0x150, 0x160, 0x170, 0x180, 0x190, 0x1A0, 0x1B0, 0x1C0,
00100     0x1D0, 0x1E0, 0x1F0, 0x200, 0x208, 0x210, 0x218, 0x220, 0x228, 0x230,
00101     0x238, 0x240, 0x248, 0x250, 0x258, 0x260, 0x268, 0x270, 0x278, 0x280,
00102     0x288, 0x290, 0x298, 0x2A0, 0x2A8, 0x2B0, 0x2B8, 0x2C0, 0x2C8, 0x2D0,
00103     0x2D8, 0x2E0, 0x2E8, 0x2F0, 0x2F8, 0x300, 0x308, 0x310, 0x318, 0x320,
00104     0x328, 0x330, 0x338, 0x340, 0x348, 0x350, 0x358, 0x360, 0x368, 0x370,
00105     0x378, 0x380, 0x388, 0x390, 0x398, 0x3A0, 0x3A8, 0x3B0, 0x3B8, 0x3C0,
00106     0x3C8, 0x3D0, 0x3D8, 0x3E0, 0x3E8, 0x3F0, 0x3F8, 0x400, 0x440, 0x480,
00107     0x4C0, 0x500, 0x540, 0x580, 0x5C0, 0x600, 0x640, 0x680, 0x6C0, 0x700,
00108     0x740, 0x780, 0x7C0, 0x800, 0x900, 0xA00, 0xB00, 0xC00, 0xD00, 0xE00,
00109     0xF00, 0x1000, 0x1400, 0x1800, 0x1C00, 0x2000, 0x3000, 0x4000
00110 };
00111 
00112 
00113 
00114 static av_cold int dpcm_decode_init(AVCodecContext *avctx)
00115 {
00116     DPCMContext *s = avctx->priv_data;
00117     int i;
00118     short square;
00119 
00120     s->channels = avctx->channels;
00121     s->sample[0] = s->sample[1] = 0;
00122 
00123     switch(avctx->codec->id) {
00124 
00125     case CODEC_ID_ROQ_DPCM:
00126         /* initialize square table */
00127         for (i = 0; i < 128; i++) {
00128             square = i * i;
00129             s->roq_square_array[i] = square;
00130             s->roq_square_array[i + 128] = -square;
00131         }
00132         break;
00133 
00134 
00135     case CODEC_ID_SOL_DPCM:
00136         switch(avctx->codec_tag){
00137         case 1:
00138             s->sol_table=sol_table_old;
00139             s->sample[0] = s->sample[1] = 0x80;
00140             break;
00141         case 2:
00142             s->sol_table=sol_table_new;
00143             s->sample[0] = s->sample[1] = 0x80;
00144             break;
00145         case 3:
00146             s->sol_table=sol_table_16;
00147             break;
00148         default:
00149             av_log(avctx, AV_LOG_ERROR, "Unknown SOL subcodec\n");
00150             return -1;
00151         }
00152         break;
00153 
00154     default:
00155         break;
00156     }
00157 
00158     avctx->sample_fmt = AV_SAMPLE_FMT_S16;
00159     return 0;
00160 }
00161 
00162 static int dpcm_decode_frame(AVCodecContext *avctx,
00163                              void *data, int *data_size,
00164                              AVPacket *avpkt)
00165 {
00166     const uint8_t *buf = avpkt->data;
00167     int buf_size = avpkt->size;
00168     DPCMContext *s = avctx->priv_data;
00169     int in, out = 0;
00170     int predictor[2];
00171     int channel_number = 0;
00172     int stereo = s->channels - 1;
00173     short *output_samples = data;
00174     int shift[2];
00175     unsigned char byte;
00176     short diff;
00177 
00178     if (!buf_size)
00179         return 0;
00180 
00181     if (stereo && (buf_size & 1))
00182         buf_size--;
00183 
00184     // almost every DPCM variant expands one byte of data into two
00185     if(*data_size/2 < buf_size)
00186         return -1;
00187 
00188     switch(avctx->codec->id) {
00189 
00190     case CODEC_ID_ROQ_DPCM:
00191         if (s->channels == 1)
00192             predictor[0] = AV_RL16(&buf[6]);
00193         else {
00194             predictor[0] = buf[7] << 8;
00195             predictor[1] = buf[6] << 8;
00196         }
00197         SE_16BIT(predictor[0]);
00198         SE_16BIT(predictor[1]);
00199 
00200         /* decode the samples */
00201         for (in = 8, out = 0; in < buf_size; in++, out++) {
00202             predictor[channel_number] += s->roq_square_array[buf[in]];
00203             predictor[channel_number] = av_clip_int16(predictor[channel_number]);
00204             output_samples[out] = predictor[channel_number];
00205 
00206             /* toggle channel */
00207             channel_number ^= s->channels - 1;
00208         }
00209         break;
00210 
00211     case CODEC_ID_INTERPLAY_DPCM:
00212         in = 6;  /* skip over the stream mask and stream length */
00213         predictor[0] = AV_RL16(&buf[in]);
00214         in += 2;
00215         SE_16BIT(predictor[0])
00216         output_samples[out++] = predictor[0];
00217         if (s->channels == 2) {
00218             predictor[1] = AV_RL16(&buf[in]);
00219             in += 2;
00220             SE_16BIT(predictor[1])
00221             output_samples[out++] = predictor[1];
00222         }
00223 
00224         while (in < buf_size) {
00225             predictor[channel_number] += interplay_delta_table[buf[in++]];
00226             predictor[channel_number] = av_clip_int16(predictor[channel_number]);
00227             output_samples[out++] = predictor[channel_number];
00228 
00229             /* toggle channel */
00230             channel_number ^= s->channels - 1;
00231         }
00232 
00233         break;
00234 
00235     case CODEC_ID_XAN_DPCM:
00236         in = 0;
00237         shift[0] = shift[1] = 4;
00238         predictor[0] = AV_RL16(&buf[in]);
00239         in += 2;
00240         SE_16BIT(predictor[0]);
00241         if (s->channels == 2) {
00242             predictor[1] = AV_RL16(&buf[in]);
00243             in += 2;
00244             SE_16BIT(predictor[1]);
00245         }
00246 
00247         while (in < buf_size) {
00248             byte = buf[in++];
00249             diff = (byte & 0xFC) << 8;
00250             if ((byte & 0x03) == 3)
00251                 shift[channel_number]++;
00252             else
00253                 shift[channel_number] -= (2 * (byte & 3));
00254             /* saturate the shifter to a lower limit of 0 */
00255             if (shift[channel_number] < 0)
00256                 shift[channel_number] = 0;
00257 
00258             diff >>= shift[channel_number];
00259             predictor[channel_number] += diff;
00260 
00261             predictor[channel_number] = av_clip_int16(predictor[channel_number]);
00262             output_samples[out++] = predictor[channel_number];
00263 
00264             /* toggle channel */
00265             channel_number ^= s->channels - 1;
00266         }
00267         break;
00268     case CODEC_ID_SOL_DPCM:
00269         in = 0;
00270         if (avctx->codec_tag != 3) {
00271             if(*data_size/4 < buf_size)
00272                 return -1;
00273             while (in < buf_size) {
00274                 int n1, n2;
00275                 n1 = (buf[in] >> 4) & 0xF;
00276                 n2 = buf[in++] & 0xF;
00277                 s->sample[0] += s->sol_table[n1];
00278                 if (s->sample[0] < 0) s->sample[0] = 0;
00279                 if (s->sample[0] > 255) s->sample[0] = 255;
00280                 output_samples[out++] = (s->sample[0] - 128) << 8;
00281                 s->sample[s->channels - 1] += s->sol_table[n2];
00282                 if (s->sample[s->channels - 1] < 0) s->sample[s->channels - 1] = 0;
00283                 if (s->sample[s->channels - 1] > 255) s->sample[s->channels - 1] = 255;
00284                 output_samples[out++] = (s->sample[s->channels - 1] - 128) << 8;
00285             }
00286         } else {
00287             while (in < buf_size) {
00288                 int n;
00289                 n = buf[in++];
00290                 if (n & 0x80) s->sample[channel_number] -= s->sol_table[n & 0x7F];
00291                 else s->sample[channel_number] += s->sol_table[n & 0x7F];
00292                 s->sample[channel_number] = av_clip_int16(s->sample[channel_number]);
00293                 output_samples[out++] = s->sample[channel_number];
00294                 /* toggle channel */
00295                 channel_number ^= s->channels - 1;
00296             }
00297         }
00298         break;
00299     }
00300 
00301     *data_size = out * sizeof(short);
00302     return avpkt->size;
00303 }
00304 
00305 #define DPCM_DECODER(id, name, long_name_)      \
00306 AVCodec ff_ ## name ## _decoder = {             \
00307     #name,                                      \
00308     AVMEDIA_TYPE_AUDIO,                         \
00309     id,                                         \
00310     sizeof(DPCMContext),                        \
00311     dpcm_decode_init,                           \
00312     NULL,                                       \
00313     NULL,                                       \
00314     dpcm_decode_frame,                          \
00315     .long_name = NULL_IF_CONFIG_SMALL(long_name_), \
00316 }
00317 
00318 DPCM_DECODER(CODEC_ID_INTERPLAY_DPCM, interplay_dpcm, "DPCM Interplay");
00319 DPCM_DECODER(CODEC_ID_ROQ_DPCM, roq_dpcm, "DPCM id RoQ");
00320 DPCM_DECODER(CODEC_ID_SOL_DPCM, sol_dpcm, "DPCM Sol");
00321 DPCM_DECODER(CODEC_ID_XAN_DPCM, xan_dpcm, "DPCM Xan");

Generated on Fri Feb 22 2013 07:24:26 for FFmpeg by  doxygen 1.7.1