vmdav.c
上传用户:wstnjxml
上传日期:2014-04-03
资源大小:7248k
文件大小:17k
源码类别:

Windows CE

开发平台:

C/C++

  1. /*
  2.  * Sierra VMD Audio & Video Decoders
  3.  * Copyright (C) 2004 the ffmpeg project
  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.  */
  20. /**
  21.  * @file vmdvideo.c
  22.  * Sierra VMD audio & video decoders
  23.  * by Vladimir "VAG" Gneushev (vagsoft at mail.ru)
  24.  * for more information on the Sierra VMD format, visit:
  25.  *   http://www.pcisys.net/~melanson/codecs/
  26.  *
  27.  * The video decoder outputs PAL8 colorspace data. The decoder expects
  28.  * a 0x330-byte VMD file header to be transmitted via extradata during
  29.  * codec initialization. Each encoded frame that is sent to this decoder
  30.  * is expected to be prepended with the appropriate 16-byte frame 
  31.  * information record from the VMD file.
  32.  *
  33.  * The audio decoder, like the video decoder, expects each encoded data
  34.  * chunk to be prepended with the appropriate 16-byte frame information
  35.  * record from the VMD file. It does not require the 0x330-byte VMD file
  36.  * header, but it does need the audio setup parameters passed in through
  37.  * normal libavcodec API means.
  38.  */
  39. #include <stdio.h>
  40. #include <stdlib.h>
  41. #include <string.h>
  42. #include <unistd.h>
  43. #include "common.h"
  44. #include "avcodec.h"
  45. #include "dsputil.h"
  46. #define VMD_HEADER_SIZE 0x330
  47. #define PALETTE_COUNT 256
  48. /*
  49.  * Video Decoder
  50.  */
  51. typedef struct VmdVideoContext {
  52.     AVCodecContext *avctx;
  53.     DSPContext dsp;
  54.     AVFrame frame;
  55.     AVFrame prev_frame;
  56.     unsigned char *buf;
  57.     int size;
  58.     unsigned char palette[PALETTE_COUNT * 4];
  59.     unsigned char *unpack_buffer;
  60.     int unpack_buffer_size;
  61. } VmdVideoContext;
  62. #define QUEUE_SIZE 0x1000
  63. #define QUEUE_MASK 0x0FFF
  64. static void lz_unpack(unsigned char *src, unsigned char *dest, int dest_len)
  65. {
  66.     unsigned char *s;
  67.     unsigned char *d;
  68.     unsigned char *d_end;
  69.     unsigned char queue[QUEUE_SIZE];
  70.     unsigned int qpos;
  71.     unsigned int dataleft;
  72.     unsigned int chainofs;
  73.     unsigned int chainlen;
  74.     unsigned int speclen;
  75.     unsigned char tag;
  76.     unsigned int i, j;
  77.     s = src;
  78.     d = dest;
  79.     d_end = d + dest_len;
  80.     dataleft = LE_32(s);
  81.     s += 4;
  82.     memset(queue, QUEUE_SIZE, 0x20);
  83.     if (LE_32(s) == 0x56781234) {
  84.         s += 4;
  85.         qpos = 0x111;
  86.         speclen = 0xF + 3;
  87.     } else {
  88.         qpos = 0xFEE;
  89.         speclen = 100;  /* no speclen */
  90.     }
  91.     while (dataleft > 0) {
  92.         tag = *s++;
  93.         if ((tag == 0xFF) && (dataleft > 8)) {
  94.             if (d + 8 > d_end)
  95.                 return;
  96.             for (i = 0; i < 8; i++) {
  97.                 queue[qpos++] = *d++ = *s++;
  98.                 qpos &= QUEUE_MASK;
  99.             }
  100.             dataleft -= 8;
  101.         } else {
  102.             for (i = 0; i < 8; i++) {
  103.                 if (dataleft == 0)
  104.                     break;
  105.                 if (tag & 0x01) {
  106.                     if (d + 1 > d_end)
  107.                         return;
  108.                     queue[qpos++] = *d++ = *s++;
  109.                     qpos &= QUEUE_MASK;
  110.                     dataleft--;
  111.                 } else {
  112.                     chainofs = *s++;
  113.                     chainofs |= ((*s & 0xF0) << 4);
  114.                     chainlen = (*s++ & 0x0F) + 3;
  115.                     if (chainlen == speclen)
  116.                         chainlen = *s++ + 0xF + 3;
  117.                     if (d + chainlen > d_end)
  118.                         return;
  119.                     for (j = 0; j < chainlen; j++) {
  120.                         *d = queue[chainofs++ & QUEUE_MASK];
  121.                         queue[qpos++] = *d++;
  122.                         qpos &= QUEUE_MASK;
  123.                     }
  124.                     dataleft -= chainlen;
  125.                 }
  126.                 tag >>= 1;
  127.             }
  128.         }
  129.     }
  130. }
  131. static int rle_unpack(unsigned char *src, unsigned char *dest, 
  132.     int src_len, int dest_len)
  133. {
  134.     unsigned char *ps;
  135.     unsigned char *pd;
  136.     int i, l;
  137.     unsigned char *dest_end = dest + dest_len;
  138.     ps = src;
  139.     pd = dest;
  140.     if (src_len & 1)
  141.         *pd++ = *ps++;
  142.     src_len >>= 1;
  143.     i = 0;
  144.     do {
  145.         l = *ps++;
  146.         if (l & 0x80) {
  147.             l = (l & 0x7F) * 2;
  148.             if (pd + l > dest_end)
  149.                 return (ps - src);
  150.             memcpy(pd, ps, l);
  151.             ps += l;
  152.             pd += l;
  153.         } else {
  154.             if (pd + i > dest_end)
  155.                 return (ps - src);
  156.             for (i = 0; i < l; i++) {
  157.                 *pd++ = ps[0];
  158.                 *pd++ = ps[1];
  159.             }
  160.             ps += 2;
  161.         }
  162.         i += l;
  163.     } while (i < src_len);
  164.     return (ps - src);
  165. }
  166. static void vmd_decode(VmdVideoContext *s)
  167. {
  168.     int i;
  169.     unsigned int *palette32;
  170.     unsigned char r, g, b;
  171.     /* point to the start of the encoded data */
  172.     unsigned char *p = s->buf + 16;
  173.     unsigned char *pb;
  174.     unsigned char meth;
  175.     unsigned char *dp;   /* pointer to current frame */
  176.     unsigned char *pp;   /* pointer to previous frame */
  177.     unsigned char len;
  178.     int ofs;
  179.     int frame_x, frame_y;
  180.     int frame_width, frame_height;
  181.     int dp_size;
  182.     frame_x = LE_16(&s->buf[6]);
  183.     frame_y = LE_16(&s->buf[8]);
  184.     frame_width = LE_16(&s->buf[10]) - frame_x + 1;
  185.     frame_height = LE_16(&s->buf[12]) - frame_y + 1;
  186.     /* if only a certain region will be updated, copy the entire previous
  187.      * frame before the decode */
  188.     if (frame_x || frame_y || (frame_width != s->avctx->width) ||
  189.         (frame_height != s->avctx->height)) {
  190.         memcpy(s->frame.data[0], s->prev_frame.data[0], 
  191.             s->avctx->height * s->frame.linesize[0]);
  192.     }
  193.     /* check if there is a new palette */
  194.     if (s->buf[15] & 0x02) {
  195.         p += 2;
  196.         palette32 = (unsigned int *)s->palette;
  197.         for (i = 0; i < PALETTE_COUNT; i++) {
  198.             r = *p++ * 4;
  199.             g = *p++ * 4;
  200.             b = *p++ * 4;
  201.             palette32[i] = (r << 16) | (g << 8) | (b);
  202.         }
  203.         s->size -= (256 * 3 + 2);
  204.     }
  205.     if (s->size >= 0) {
  206.         /* originally UnpackFrame in VAG's code */
  207.         pb = p;
  208.         meth = *pb++;
  209.         if (meth & 0x80) {
  210.             lz_unpack(pb, s->unpack_buffer, s->unpack_buffer_size);
  211.             meth &= 0x7F;
  212.             pb = s->unpack_buffer;
  213.         }
  214.         dp = &s->frame.data[0][frame_y * s->frame.linesize[0] + frame_x];
  215.         dp_size = s->frame.linesize[0] * s->avctx->height;
  216.         pp = &s->prev_frame.data[0][frame_y * s->prev_frame.linesize[0] + frame_x];
  217.         switch (meth) {
  218.         case 1:
  219.             for (i = 0; i < frame_height; i++) {
  220.                 ofs = 0;
  221.                 do {
  222.                     len = *pb++;
  223.                     if (len & 0x80) {
  224.                         len = (len & 0x7F) + 1;
  225.                         if (ofs + len > frame_width)
  226.                             return;
  227.                         memcpy(&dp[ofs], pb, len);
  228.                         pb += len;
  229.                         ofs += len;
  230.                     } else {
  231.                         /* interframe pixel copy */
  232.                         if (ofs + len + 1 > frame_width)
  233.                             return;
  234.                         memcpy(&dp[ofs], &pp[ofs], len + 1);
  235.                         ofs += len + 1;
  236.                     }
  237.                 } while (ofs < frame_width);
  238.                 if (ofs > frame_width) {
  239.                     av_log(s->avctx, AV_LOG_ERROR, "VMD video: offset > width (%d > %d)n",
  240.                         ofs, frame_width);
  241.                     break;
  242.                 }
  243.                 dp += s->frame.linesize[0];
  244.                 pp += s->prev_frame.linesize[0];
  245.             }
  246.             break;
  247.         case 2:
  248.             for (i = 0; i < frame_height; i++) {
  249.                 memcpy(dp, pb, frame_width);
  250.                 pb += frame_width;
  251.                 dp += s->frame.linesize[0];
  252.                 pp += s->prev_frame.linesize[0];
  253.             }
  254.             break;
  255.         case 3:
  256.             for (i = 0; i < frame_height; i++) {
  257.                 ofs = 0;
  258.                 do {
  259.                     len = *pb++;
  260.                     if (len & 0x80) {
  261.                         len = (len & 0x7F) + 1;
  262.                         if (*pb++ == 0xFF)
  263.                             len = rle_unpack(pb, &dp[ofs], len, frame_width - ofs);
  264.                         else
  265.                             memcpy(&dp[ofs], pb, len);
  266.                         pb += len;
  267.                         ofs += len;
  268.                     } else {
  269.                         /* interframe pixel copy */
  270.                         if (ofs + len + 1 > frame_width)
  271.                             return;
  272.                         memcpy(&dp[ofs], &pp[ofs], len + 1);
  273.                         ofs += len + 1;
  274.                     }
  275.                 } while (ofs < frame_width);
  276.                 if (ofs > frame_width) {
  277.                     av_log(s->avctx, AV_LOG_ERROR, "VMD video: offset > width (%d > %d)n",
  278.                         ofs, frame_width);
  279.                 }
  280.                 dp += s->frame.linesize[0];
  281.                 pp += s->prev_frame.linesize[0];
  282.             }
  283.             break;
  284.         }
  285.     }
  286. }
  287. static int vmdvideo_decode_init(AVCodecContext *avctx)
  288. {
  289.     VmdVideoContext *s = (VmdVideoContext *)avctx->priv_data;
  290.     int i;
  291.     unsigned int *palette32;
  292.     int palette_index = 0;
  293.     unsigned char r, g, b;
  294.     unsigned char *vmd_header;
  295.     unsigned char *raw_palette;
  296.     s->avctx = avctx;
  297.     avctx->pix_fmt = PIX_FMT_PAL8;
  298.     avctx->has_b_frames = 0;
  299.     dsputil_init(&s->dsp, avctx);
  300.     /* make sure the VMD header made it */
  301.     if (s->avctx->extradata_size != VMD_HEADER_SIZE) {
  302.         av_log(s->avctx, AV_LOG_ERROR, "VMD video: expected extradata size of %dn", 
  303.             VMD_HEADER_SIZE);
  304.         return -1;
  305.     }
  306.     vmd_header = (unsigned char *)avctx->extradata;
  307.     s->unpack_buffer_size = LE_32(&vmd_header[800]);
  308.     s->unpack_buffer = av_malloc(s->unpack_buffer_size);
  309.     if (!s->unpack_buffer)
  310.         return -1;
  311.     /* load up the initial palette */
  312.     raw_palette = &vmd_header[28];
  313.     palette32 = (unsigned int *)s->palette;
  314.     for (i = 0; i < PALETTE_COUNT; i++) {
  315.         r = raw_palette[palette_index++] * 4;
  316.         g = raw_palette[palette_index++] * 4;
  317.         b = raw_palette[palette_index++] * 4;
  318.         palette32[i] = (r << 16) | (g << 8) | (b);
  319.     }
  320.     s->frame.data[0] = s->prev_frame.data[0] = NULL;
  321.     return 0;
  322. }
  323. static int vmdvideo_decode_frame(AVCodecContext *avctx,
  324.                                  void *data, int *data_size,
  325.                                  uint8_t *buf, int buf_size)
  326. {
  327.     VmdVideoContext *s = (VmdVideoContext *)avctx->priv_data;
  328.     s->buf = buf;
  329.     s->size = buf_size;
  330.     if (buf_size < 16)
  331.         return buf_size;
  332.     s->frame.reference = 1;
  333.     if (avctx->get_buffer(avctx, &s->frame)) {
  334.         av_log(s->avctx, AV_LOG_ERROR, "VMD Video: get_buffer() failedn");
  335.         return -1;
  336.     }
  337.     vmd_decode(s);
  338.     /* make the palette available on the way out */
  339.     memcpy(s->frame.data[1], s->palette, PALETTE_COUNT * 4);
  340.     if (s->prev_frame.data[0])
  341.         avctx->release_buffer(avctx, &s->prev_frame);
  342.     /* shuffle frames */
  343.     s->prev_frame = s->frame;
  344.     *data_size = sizeof(AVFrame);
  345.     *(AVFrame*)data = s->frame;
  346.     /* report that the buffer was completely consumed */
  347.     return buf_size;
  348. }
  349. static int vmdvideo_decode_end(AVCodecContext *avctx)
  350. {
  351.     VmdVideoContext *s = (VmdVideoContext *)avctx->priv_data;
  352.     if (s->prev_frame.data[0])
  353.         avctx->release_buffer(avctx, &s->prev_frame);
  354.     av_free(s->unpack_buffer);
  355.     return 0;
  356. }
  357. /*
  358.  * Audio Decoder
  359.  */
  360. typedef struct VmdAudioContext {
  361.     AVCodecContext *avctx;
  362.     int channels;
  363.     int bits;
  364.     int block_align;
  365.     unsigned char steps8[16];
  366.     unsigned short steps16[16];
  367.     unsigned short steps128[256];
  368.     short predictors[2];
  369. } VmdAudioContext;
  370. static int vmdaudio_decode_init(AVCodecContext *avctx)
  371. {
  372.     VmdAudioContext *s = (VmdAudioContext *)avctx->priv_data;
  373.     int i;
  374.     s->avctx = avctx;
  375.     s->channels = avctx->channels;
  376.     s->bits = avctx->bits_per_sample;
  377.     s->block_align = avctx->block_align;
  378.     av_log(s->avctx, AV_LOG_DEBUG, "%d channels, %d bits/sample, block align = %d, sample rate = %dn",
  379.     s->channels, s->bits, s->block_align, avctx->sample_rate);
  380.     /* set up the steps8 and steps16 tables */
  381.     for (i = 0; i < 8; i++) {
  382.         if (i < 4)
  383.             s->steps8[i] = i;
  384.         else
  385.             s->steps8[i] = s->steps8[i - 1] + i - 1;
  386.         if (i == 0)
  387.             s->steps16[i] = 0;
  388.         else if (i == 1)
  389.             s->steps16[i] = 4;
  390.         else if (i == 2)
  391.             s->steps16[i] = 16;
  392.         else
  393.             s->steps16[i] = 1 << (i + 4);
  394.     }
  395.     /* set up the step128 table */
  396.     s->steps128[0] = 0;
  397.     s->steps128[1] = 8;
  398.     for (i = 0x02; i <= 0x20; i++)
  399.         s->steps128[i] = (i - 1) << 4;
  400.     for (i = 0x21; i <= 0x60; i++)
  401.         s->steps128[i] = (i + 0x1F) << 3;
  402.     for (i = 0x61; i <= 0x70; i++)
  403.         s->steps128[i] = (i - 0x51) << 6;
  404.     for (i = 0x71; i <= 0x78; i++)
  405.         s->steps128[i] = (i - 0x69) << 8;
  406.     for (i = 0x79; i <= 0x7D; i++)
  407.         s->steps128[i] = (i - 0x75) << 10;
  408.     s->steps128[0x7E] = 0x3000;
  409.     s->steps128[0x7F] = 0x4000;
  410.     /* set up the negative half of each table */
  411.     for (i = 0; i < 8; i++) {
  412.         s->steps8[i + 8] = -s->steps8[i];
  413.         s->steps16[i + 8] = -s->steps16[i];
  414.     }
  415.     for (i = 0; i < 128; i++)
  416.       s->steps128[i + 128] = -s->steps128[i];
  417.     return 0;
  418. }
  419. static void vmdaudio_decode_audio(VmdAudioContext *s, unsigned char *data,
  420.     uint8_t *buf, int ratio) {
  421. }
  422. static int vmdaudio_loadsound(VmdAudioContext *s, unsigned char *data,
  423.     uint8_t *buf, int silence)
  424. {
  425.     int bytes_decoded = 0;
  426.     int i;
  427.     if (silence)
  428. av_log(s->avctx, AV_LOG_INFO, "silent block!n");
  429.     if (s->channels == 2) {
  430.         /* stereo handling */
  431.         if ((s->block_align & 0x01) == 0) {
  432.             if (silence)
  433.                 memset(data, 0, s->block_align * 2);
  434.             else
  435.                 vmdaudio_decode_audio(s, data, buf, 1);
  436.         } else {
  437.             if (silence)
  438.                 memset(data, 0, s->block_align * 2);
  439.             else
  440.                 vmdaudio_decode_audio(s, data, buf, 1);
  441.         }
  442.     } else {
  443.         /* mono handling */
  444.         if (silence) {
  445.             if (s->bits == 16) {
  446.                 memset(data, 0, s->block_align * 2);
  447.                 bytes_decoded = s->block_align * 2;
  448.             } else {
  449. //                memset(data, 0x00, s->block_align);
  450. //                bytes_decoded = s->block_align;
  451. memset(data, 0x00, s->block_align * 2);
  452. bytes_decoded = s->block_align * 2;
  453.             }
  454.         } else {
  455.             /* copy the data but convert it to signed */
  456.             for (i = 0; i < s->block_align; i++)
  457.                 data[i * 2 + 1] = buf[i] + 0x80;
  458.             bytes_decoded = s->block_align * 2;
  459.         }
  460.     }
  461.     return bytes_decoded;
  462. }
  463. static int vmdaudio_decode_frame(AVCodecContext *avctx,
  464.                                  void *data, int *data_size,
  465.                                  uint8_t *buf, int buf_size)
  466. {
  467.     VmdAudioContext *s = (VmdAudioContext *)avctx->priv_data;
  468.     unsigned int sound_flags;
  469.     unsigned char *output_samples = (unsigned char *)data;
  470.     /* point to the start of the encoded data */
  471.     unsigned char *p = buf + 16;
  472.     unsigned char *p_end = buf + buf_size;
  473.     if (buf_size < 16)
  474.         return buf_size;
  475.     if (buf[6] == 1) {
  476.         /* the chunk contains audio */
  477.         *data_size = vmdaudio_loadsound(s, output_samples, p, 0);
  478.     } else if (buf[6] == 2) {
  479.         /* the chunk contains audio and silence mixed together */
  480.         sound_flags = LE_32(p);
  481.         p += 4;
  482.         /* do something with extrabufs here? */
  483.         while (p < p_end) {
  484.             if (sound_flags & 0x01)
  485.                 /* silence */
  486.                 *data_size += vmdaudio_loadsound(s, output_samples, p, 1);
  487.             else {
  488.                 /* audio */
  489.                 *data_size += vmdaudio_loadsound(s, output_samples, p, 0);
  490.                 p += s->block_align;
  491.             }
  492.             output_samples += (s->block_align * s->bits / 8);
  493.             sound_flags >>= 1;
  494.         }
  495.     } else if (buf[6] == 3) {
  496.         /* silent chunk */
  497.         *data_size = vmdaudio_loadsound(s, output_samples, p, 1);
  498.     }
  499.     return buf_size;
  500. }
  501. /*
  502.  * Public Data Structures
  503.  */
  504. AVCodec vmdvideo_decoder = {
  505.     "vmdvideo",
  506.     CODEC_TYPE_VIDEO,
  507.     CODEC_ID_VMDVIDEO,
  508.     sizeof(VmdVideoContext),
  509.     vmdvideo_decode_init,
  510.     NULL,
  511.     vmdvideo_decode_end,
  512.     vmdvideo_decode_frame,
  513.     CODEC_CAP_DR1,
  514. };
  515. AVCodec vmdaudio_decoder = {
  516.     "vmdaudio",
  517.     CODEC_TYPE_AUDIO,
  518.     CODEC_ID_VMDAUDIO,
  519.     sizeof(VmdAudioContext),
  520.     vmdaudio_decode_init,
  521.     NULL,
  522.     NULL,
  523.     vmdaudio_decode_frame,
  524. };