home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 10 Tools / 10-Tools.zip / wvis0626.zip / warpvision_20020626.zip / libavcodec / pcm.c < prev    next >
C/C++ Source or Header  |  2002-06-19  |  10KB  |  373 lines

  1. /*
  2.  * PCM codecs
  3.  * Copyright (c) 2001 Fabrice Bellard.
  4.  *
  5.  * This library is free software; you can redistribute it and/or
  6.  * modify it under the terms of the GNU Lesser General Public
  7.  * License as published by the Free Software Foundation; either
  8.  * version 2 of the License, or (at your option) any later version.
  9.  *
  10.  * This library is distributed in the hope that it will be useful,
  11.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  12.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  13.  * Lesser General Public License for more details.
  14.  *
  15.  * You should have received a copy of the GNU Lesser General Public
  16.  * License along with this library; if not, write to the Free Software
  17.  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  18.  */
  19. #include "avcodec.h"
  20.  
  21. /* from g711.c by SUN microsystems (unrestricted use) */
  22.  
  23. #define    SIGN_BIT    (0x80)        /* Sign bit for a A-law byte. */
  24. #define    QUANT_MASK    (0xf)        /* Quantization field mask. */
  25. #define    NSEGS        (8)        /* Number of A-law segments. */
  26. #define    SEG_SHIFT    (4)        /* Left shift for segment number. */
  27. #define    SEG_MASK    (0x70)        /* Segment field mask. */
  28.  
  29. #define    BIAS        (0x84)        /* Bias for linear code. */
  30.  
  31. /*
  32.  * alaw2linear() - Convert an A-law value to 16-bit linear PCM
  33.  *
  34.  */
  35. static int alaw2linear(unsigned char    a_val)
  36. {
  37.     int        t;
  38.     int        seg;
  39.  
  40.     a_val ^= 0x55;
  41.  
  42.     t = (a_val & QUANT_MASK) << 4;
  43.     seg = ((unsigned)a_val & SEG_MASK) >> SEG_SHIFT;
  44.     switch (seg) {
  45.     case 0:
  46.         t += 8;
  47.         break;
  48.     case 1:
  49.         t += 0x108;
  50.         break;
  51.     default:
  52.         t += 0x108;
  53.         t <<= seg - 1;
  54.     }
  55.     return ((a_val & SIGN_BIT) ? t : -t);
  56. }
  57.  
  58. static int ulaw2linear(unsigned char    u_val)
  59. {
  60.     int        t;
  61.  
  62.     /* Complement to obtain normal u-law value. */
  63.     u_val = ~u_val;
  64.  
  65.     /*
  66.      * Extract and bias the quantization bits. Then
  67.      * shift up by the segment number and subtract out the bias.
  68.      */
  69.     t = ((u_val & QUANT_MASK) << 3) + BIAS;
  70.     t <<= ((unsigned)u_val & SEG_MASK) >> SEG_SHIFT;
  71.  
  72.     return ((u_val & SIGN_BIT) ? (BIAS - t) : (t - BIAS));
  73. }
  74.  
  75. /* 16384 entries per table */
  76. static UINT8 *linear_to_alaw = NULL;
  77. static int linear_to_alaw_ref = 0;
  78.  
  79. static UINT8 *linear_to_ulaw = NULL;
  80. static int linear_to_ulaw_ref = 0;
  81.  
  82. static void build_xlaw_table(UINT8 *linear_to_xlaw, 
  83.                              int (*xlaw2linear)(unsigned char),
  84.                              int mask) 
  85. {
  86.     int i, j, v, v1, v2;
  87.  
  88.     j = 0;
  89.     for(i=0;i<128;i++) {
  90.         if (i != 127) {
  91.             v1 = xlaw2linear(i ^ mask);
  92.             v2 = xlaw2linear((i + 1) ^ mask);
  93.             v = (v1 + v2 + 4) >> 3;
  94.         } else {
  95.             v = 8192;
  96.         }
  97.         for(;j<v;j++) {
  98.             linear_to_xlaw[8192 + j] = (i ^ mask);
  99.             if (j > 0)
  100.                 linear_to_xlaw[8192 - j] = (i ^ (mask ^ 0x80));
  101.         }
  102.     }
  103.     linear_to_xlaw[0] = linear_to_xlaw[1];
  104. }
  105.  
  106. static int pcm_encode_init(AVCodecContext *avctx)
  107. {
  108.     avctx->frame_size = 1;
  109.     switch(avctx->codec->id) {
  110.     case CODEC_ID_PCM_ALAW:
  111.         if (linear_to_alaw_ref == 0) {
  112.             linear_to_alaw = av_malloc(16384);
  113.             if (!linear_to_alaw)
  114.                 return -1;
  115.             build_xlaw_table(linear_to_alaw, alaw2linear, 0xd5);
  116.         }
  117.         linear_to_alaw_ref++;
  118.         break;
  119.     case CODEC_ID_PCM_MULAW:
  120.         if (linear_to_ulaw_ref == 0) {
  121.             linear_to_ulaw = av_malloc(16384);
  122.             if (!linear_to_ulaw)
  123.                 return -1;
  124.             build_xlaw_table(linear_to_ulaw, ulaw2linear, 0xff);
  125.         }
  126.         linear_to_ulaw_ref++;
  127.         break;
  128.     default:
  129.         break;
  130.     }
  131.     return 0;
  132. }
  133.  
  134. static int pcm_encode_close(AVCodecContext *avctx)
  135. {
  136.     switch(avctx->codec->id) {
  137.     case CODEC_ID_PCM_ALAW:
  138.         if (--linear_to_alaw_ref == 0)
  139.             av_free(linear_to_alaw);
  140.         break;
  141.     case CODEC_ID_PCM_MULAW:
  142.         if (--linear_to_ulaw_ref == 0)
  143.             av_free(linear_to_ulaw);
  144.         break;
  145.     default:
  146.         /* nothing to free */
  147.         break;
  148.     }
  149.     return 0;
  150. }
  151.  
  152. static int pcm_encode_frame(AVCodecContext *avctx,
  153.                 unsigned char *frame, int buf_size, void *data)
  154. {
  155.     int n, sample_size, v;
  156.     short *samples;
  157.     unsigned char *dst;
  158.  
  159.     switch(avctx->codec->id) {
  160.     case CODEC_ID_PCM_S16LE:
  161.     case CODEC_ID_PCM_S16BE:
  162.     case CODEC_ID_PCM_U16LE:
  163.     case CODEC_ID_PCM_U16BE:
  164.         sample_size = 2;
  165.         break;
  166.     default:
  167.         sample_size = 1;
  168.         break;
  169.     }
  170.     n = buf_size / sample_size;
  171.     samples = data;
  172.     dst = frame;
  173.  
  174.     switch(avctx->codec->id) {
  175.     case CODEC_ID_PCM_S16LE:
  176.         for(;n>0;n--) {
  177.             v = *samples++;
  178.             dst[0] = v & 0xff;
  179.             dst[1] = v >> 8;
  180.             dst += 2;
  181.         }
  182.         break;
  183.     case CODEC_ID_PCM_S16BE:
  184.         for(;n>0;n--) {
  185.             v = *samples++;
  186.             dst[0] = v >> 8;
  187.             dst[1] = v;
  188.             dst += 2;
  189.         }
  190.         break;
  191.     case CODEC_ID_PCM_U16LE:
  192.         for(;n>0;n--) {
  193.             v = *samples++;
  194.             v += 0x8000;
  195.             dst[0] = v & 0xff;
  196.             dst[1] = v >> 8;
  197.             dst += 2;
  198.         }
  199.         break;
  200.     case CODEC_ID_PCM_U16BE:
  201.         for(;n>0;n--) {
  202.             v = *samples++;
  203.             v += 0x8000;
  204.             dst[0] = v >> 8;
  205.             dst[1] = v;
  206.             dst += 2;
  207.         }
  208.         break;
  209.     case CODEC_ID_PCM_S8:
  210.         for(;n>0;n--) {
  211.             v = *samples++;
  212.             dst[0] = (v + 128) >> 8;
  213.             dst++;
  214.         }
  215.         break;
  216.     case CODEC_ID_PCM_U8:
  217.         for(;n>0;n--) {
  218.             v = *samples++;
  219.             dst[0] = ((v + 128) >> 8) + 128;
  220.             dst++;
  221.         }
  222.         break;
  223.     case CODEC_ID_PCM_ALAW:
  224.         for(;n>0;n--) {
  225.             v = *samples++;
  226.             dst[0] = linear_to_alaw[(v + 32768) >> 2];
  227.             dst++;
  228.         }
  229.         break;
  230.     case CODEC_ID_PCM_MULAW:
  231.         for(;n>0;n--) {
  232.             v = *samples++;
  233.             dst[0] = linear_to_ulaw[(v + 32768) >> 2];
  234.             dst++;
  235.         }
  236.         break;
  237.     default:
  238.         return -1;
  239.     }
  240.     avctx->key_frame = 1;
  241.     //avctx->frame_size = (dst - frame) / (sample_size * avctx->channels);
  242.  
  243.     return dst - frame;
  244. }
  245.  
  246. typedef struct PCMDecode {
  247.     short table[256];
  248. } PCMDecode;
  249.  
  250. static int pcm_decode_init(AVCodecContext * avctx)
  251. {
  252.     PCMDecode *s = avctx->priv_data;
  253.     int i;
  254.  
  255.     switch(avctx->codec->id) {
  256.     case CODEC_ID_PCM_ALAW:
  257.         for(i=0;i<256;i++)
  258.             s->table[i] = alaw2linear(i);
  259.         break;
  260.     case CODEC_ID_PCM_MULAW:
  261.         for(i=0;i<256;i++)
  262.             s->table[i] = ulaw2linear(i);
  263.         break;
  264.     default:
  265.         break;
  266.     }
  267.     return 0;
  268. }
  269.  
  270. static int pcm_decode_frame(AVCodecContext *avctx,
  271.                 void *data, int *data_size,
  272.                 UINT8 *buf, int buf_size)
  273. {
  274.     PCMDecode *s = avctx->priv_data;
  275.     int n;
  276.     short *samples;
  277.     UINT8 *src;
  278.  
  279.     samples = data;
  280.     src = buf;
  281.  
  282.     switch(avctx->codec->id) {
  283.     case CODEC_ID_PCM_S16LE:
  284.         n = buf_size >> 1;
  285.         for(;n>0;n--) {
  286.             *samples++ = src[0] | (src[1] << 8);
  287.             src += 2;
  288.         }
  289.         break;
  290.     case CODEC_ID_PCM_S16BE:
  291.         n = buf_size >> 1;
  292.         for(;n>0;n--) {
  293.             *samples++ = (src[0] << 8) | src[1];
  294.             src += 2;
  295.         }
  296.         break;
  297.     case CODEC_ID_PCM_U16LE:
  298.         n = buf_size >> 1;
  299.         for(;n>0;n--) {
  300.             *samples++ = (src[0] | (src[1] << 8)) - 0x8000;
  301.             src += 2;
  302.         }
  303.         break;
  304.     case CODEC_ID_PCM_U16BE:
  305.         n = buf_size >> 1;
  306.         for(;n>0;n--) {
  307.             *samples++ = ((src[0] << 8) | src[1]) - 0x8000;
  308.             src += 2;
  309.         }
  310.         break;
  311.     case CODEC_ID_PCM_S8:
  312.         n = buf_size;
  313.         for(;n>0;n--) {
  314.             *samples++ = src[0] << 8;
  315.             src++;
  316.         }
  317.         break;
  318.     case CODEC_ID_PCM_U8:
  319.         n = buf_size;
  320.         for(;n>0;n--) {
  321.             *samples++ = ((int)src[0] - 128) << 8;
  322.             src++;
  323.         }
  324.         break;
  325.     case CODEC_ID_PCM_ALAW:
  326.     case CODEC_ID_PCM_MULAW:
  327.         n = buf_size;
  328.         for(;n>0;n--) {
  329.             *samples++ = s->table[src[0]];
  330.             src++;
  331.         }
  332.         break;
  333.     default:
  334.         *data_size = 0;
  335.         return -1;
  336.     }
  337.     *data_size = (UINT8 *)samples - (UINT8 *)data;
  338.     return src - buf;
  339. }
  340.  
  341. #define PCM_CODEC(id, name)                     \
  342. AVCodec name ## _encoder = {                    \
  343.     #name,                                      \
  344.     CODEC_TYPE_AUDIO,                           \
  345.     id,                                         \
  346.     0,                                          \
  347.     pcm_encode_init,                \
  348.     pcm_encode_frame,                \
  349.     pcm_encode_close,                \
  350.     NULL,                                       \
  351. };                                              \
  352. AVCodec name ## _decoder = {                    \
  353.     #name,                                      \
  354.     CODEC_TYPE_AUDIO,                           \
  355.     id,                                         \
  356.     sizeof(PCMDecode),                          \
  357.     pcm_decode_init,                \
  358.     NULL,                                       \
  359.     NULL,                                       \
  360.     pcm_decode_frame,                           \
  361. };
  362.  
  363. PCM_CODEC(CODEC_ID_PCM_S16LE, pcm_s16le);
  364. PCM_CODEC(CODEC_ID_PCM_S16BE, pcm_s16be);
  365. PCM_CODEC(CODEC_ID_PCM_U16LE, pcm_u16le);
  366. PCM_CODEC(CODEC_ID_PCM_U16BE, pcm_u16be);
  367. PCM_CODEC(CODEC_ID_PCM_S8, pcm_s8);
  368. PCM_CODEC(CODEC_ID_PCM_U8, pcm_u8);
  369. PCM_CODEC(CODEC_ID_PCM_ALAW, pcm_alaw);
  370. PCM_CODEC(CODEC_ID_PCM_MULAW, pcm_mulaw);
  371.  
  372. #undef PCM_CODEC
  373.