Subversion Repositories Kolibri OS

Rev

Blame | Last modification | View Log | RSS feed

  1. /*
  2.  * LucasArts VIMA decoder
  3.  * Copyright (c) 2012 Paul B Mahol
  4.  *
  5.  * This file is part of FFmpeg.
  6.  *
  7.  * FFmpeg is free software; you can redistribute it and/or
  8.  * modify it under the terms of the GNU Lesser General Public
  9.  * License as published by the Free Software Foundation; either
  10.  * version 2.1 of the License, or (at your option) any later version.
  11.  *
  12.  * FFmpeg is distributed in the hope that it will be useful,
  13.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  14.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  15.  * Lesser General Public License for more details.
  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
  20.  */
  21.  
  22. /**
  23.  * @file
  24.  * LucasArts VIMA audio decoder
  25.  * @author Paul B Mahol
  26.  */
  27.  
  28. #include "libavutil/channel_layout.h"
  29.  
  30. #include "adpcm_data.h"
  31. #include "avcodec.h"
  32. #include "get_bits.h"
  33. #include "internal.h"
  34.  
  35. static int predict_table_init = 0;
  36. static uint16_t predict_table[5786 * 2];
  37.  
  38. static const uint8_t size_table[] = {
  39.     4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
  40.     4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
  41.     4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
  42.     5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,
  43.     6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
  44.     7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7
  45. };
  46.  
  47. static const int8_t index_table1[] = {
  48.     -1, 4, -1, 4
  49. };
  50.  
  51. static const int8_t index_table2[] = {
  52.     -1, -1, 2, 6, -1, -1, 2, 6
  53. };
  54.  
  55. static const int8_t index_table3[] = {
  56.     -1, -1, -1, -1, 1, 2, 4, 6, -1, -1, -1, -1, 1, 2, 4, 6
  57. };
  58.  
  59. static const int8_t index_table4[] = {
  60.     -1, -1, -1, -1, -1, -1, -1, -1, 1,  1,  1,  2,  2,  4,  5,  6,
  61.     -1, -1, -1, -1, -1, -1, -1, -1, 1,  1,  1,  2,  2,  4,  5,  6
  62. };
  63.  
  64. static const int8_t index_table5[] = {
  65.     -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
  66.      1,  1,  1,  1,  1,  2,  2,  2,  2,  4,  4,  4,  5,  5,  6,  6,
  67.     -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
  68.      1,  1,  1,  1,  1,  2,  2,  2,  2,  4,  4,  4,  5,  5,  6,  6
  69. };
  70.  
  71. static const int8_t index_table6[] = {
  72.     -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
  73.     -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
  74.      1,  1,  1,  1,  1,  1,  1,  1,  1,  1,  2,  2,  2,  2,  2,  2,
  75.      2,  2,  4,  4,  4,  4,  4,  4,  5,  5,  5,  5,  6,  6,  6,  6,
  76.     -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
  77.     -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
  78.      1,  1,  1,  1,  1,  1,  1,  1,  1,  1,  2,  2,  2,  2,  2,  2,
  79.      2,  2,  4,  4,  4,  4,  4,  4,  5,  5,  5,  5,  6,  6,  6,  6
  80. };
  81.  
  82. static const int8_t *const step_index_tables[] = {
  83.     index_table1, index_table2, index_table3,
  84.     index_table4, index_table5, index_table6
  85. };
  86.  
  87. static av_cold int decode_init(AVCodecContext *avctx)
  88. {
  89.     int start_pos;
  90.  
  91.     avctx->sample_fmt = AV_SAMPLE_FMT_S16;
  92.  
  93.     if (predict_table_init)
  94.         return 0;
  95.  
  96.     for (start_pos = 0; start_pos < 64; start_pos++) {
  97.         unsigned int dest_pos, table_pos;
  98.  
  99.         for (table_pos = 0, dest_pos = start_pos;
  100.              table_pos < FF_ARRAY_ELEMS(ff_adpcm_step_table);
  101.              table_pos++, dest_pos += 64) {
  102.             int put = 0, count, table_value;
  103.  
  104.             table_value = ff_adpcm_step_table[table_pos];
  105.             for (count = 32; count != 0; count >>= 1) {
  106.                 if (start_pos & count)
  107.                     put += table_value;
  108.                 table_value >>= 1;
  109.             }
  110.             predict_table[dest_pos] = put;
  111.         }
  112.     }
  113.     predict_table_init = 1;
  114.  
  115.     return 0;
  116. }
  117.  
  118. static int decode_frame(AVCodecContext *avctx, void *data,
  119.                         int *got_frame_ptr, AVPacket *pkt)
  120. {
  121.     GetBitContext gb;
  122.     AVFrame *frame = data;
  123.     int16_t pcm_data[2];
  124.     uint32_t samples;
  125.     int8_t channel_hint[2];
  126.     int ret, chan;
  127.     int channels = 1;
  128.  
  129.     if (pkt->size < 13)
  130.         return AVERROR_INVALIDDATA;
  131.  
  132.     if ((ret = init_get_bits8(&gb, pkt->data, pkt->size)) < 0)
  133.         return ret;
  134.  
  135.     samples = get_bits_long(&gb, 32);
  136.     if (samples == 0xffffffff) {
  137.         skip_bits_long(&gb, 32);
  138.         samples = get_bits_long(&gb, 32);
  139.     }
  140.  
  141.     if (samples > pkt->size * 2)
  142.         return AVERROR_INVALIDDATA;
  143.  
  144.     channel_hint[0] = get_sbits(&gb, 8);
  145.     if (channel_hint[0] & 0x80) {
  146.         channel_hint[0] = ~channel_hint[0];
  147.         channels = 2;
  148.     }
  149.     avctx->channels = channels;
  150.     avctx->channel_layout = (channels == 2) ? AV_CH_LAYOUT_STEREO
  151.                                             : AV_CH_LAYOUT_MONO;
  152.     pcm_data[0] = get_sbits(&gb, 16);
  153.     if (channels > 1) {
  154.         channel_hint[1] = get_sbits(&gb, 8);
  155.         pcm_data[1]     = get_sbits(&gb, 16);
  156.     }
  157.  
  158.     frame->nb_samples = samples;
  159.     if ((ret = ff_get_buffer(avctx, frame, 0)) < 0)
  160.         return ret;
  161.  
  162.     for (chan = 0; chan < channels; chan++) {
  163.         uint16_t *dest = (uint16_t *)frame->data[0] + chan;
  164.         int step_index = channel_hint[chan];
  165.         int output = pcm_data[chan];
  166.         int sample;
  167.  
  168.         for (sample = 0; sample < samples; sample++) {
  169.             int lookup_size, lookup, highbit, lowbits;
  170.  
  171.             step_index  = av_clip(step_index, 0, 88);
  172.             lookup_size = size_table[step_index];
  173.             lookup      = get_bits(&gb, lookup_size);
  174.             highbit     = 1 << (lookup_size - 1);
  175.             lowbits     = highbit - 1;
  176.  
  177.             if (lookup & highbit)
  178.                 lookup ^= highbit;
  179.             else
  180.                 highbit = 0;
  181.  
  182.             if (lookup == lowbits) {
  183.                 output = get_sbits(&gb, 16);
  184.             } else {
  185.                 int predict_index, diff;
  186.  
  187.                 predict_index = (lookup << (7 - lookup_size)) | (step_index << 6);
  188.                 predict_index = av_clip(predict_index, 0, 5785);
  189.                 diff          = predict_table[predict_index];
  190.                 if (lookup)
  191.                     diff += ff_adpcm_step_table[step_index] >> (lookup_size - 1);
  192.                 if (highbit)
  193.                     diff = -diff;
  194.  
  195.                 output = av_clip_int16(output + diff);
  196.             }
  197.  
  198.             *dest = output;
  199.             dest += channels;
  200.  
  201.             step_index += step_index_tables[lookup_size - 2][lookup];
  202.         }
  203.     }
  204.  
  205.     *got_frame_ptr = 1;
  206.  
  207.     return pkt->size;
  208. }
  209.  
  210. AVCodec ff_adpcm_vima_decoder = {
  211.     .name         = "adpcm_vima",
  212.     .long_name    = NULL_IF_CONFIG_SMALL("LucasArts VIMA audio"),
  213.     .type         = AVMEDIA_TYPE_AUDIO,
  214.     .id           = AV_CODEC_ID_ADPCM_VIMA,
  215.     .init         = decode_init,
  216.     .decode       = decode_frame,
  217.     .capabilities = AV_CODEC_CAP_DR1,
  218. };
  219.  
  220. #if FF_API_VIMA_DECODER
  221. AVCodec ff_vima_decoder = {
  222.     .name         = "vima",
  223.     .long_name    = NULL_IF_CONFIG_SMALL("LucasArts VIMA audio"),
  224.     .type         = AVMEDIA_TYPE_AUDIO,
  225.     .id           = AV_CODEC_ID_ADPCM_VIMA,
  226.     .init         = decode_init,
  227.     .decode       = decode_frame,
  228.     .capabilities = AV_CODEC_CAP_DR1,
  229. };
  230. #endif
  231.