Subversion Repositories Kolibri OS

Rev

Blame | Last modification | View Log | RSS feed

  1. /*
  2.  * TDSC decoder
  3.  * Copyright (C) 2015 Vittorio Giovara <vittorio.giovara@gmail.com>
  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.  * TDSC decoder
  25.  *
  26.  * Fourcc: TSDC
  27.  *
  28.  * TDSC is very simple. It codes picture by tiles, storing them in raw BGR24
  29.  * format or compressing them in JPEG. Frames can be full pictures or just
  30.  * updates to the previous frame. Cursor is found in its own frame or at the
  31.  * bottom of the picture. Every frame is then packed with zlib.
  32.  *
  33.  * Supports: BGR24
  34.  */
  35.  
  36. #include <stdint.h>
  37. #include <zlib.h>
  38.  
  39. #include "libavutil/imgutils.h"
  40.  
  41. #include "avcodec.h"
  42. #include "bytestream.h"
  43. #include "internal.h"
  44.  
  45. #define BITMAPINFOHEADER_SIZE 0x28
  46. #define TDSF_HEADER_SIZE      0x56
  47. #define TDSB_HEADER_SIZE      0x08
  48.  
  49. typedef struct TDSCContext {
  50.     AVCodecContext *jpeg_avctx;   // wrapper context for MJPEG
  51.  
  52.     int width, height;
  53.     GetByteContext gbc;
  54.  
  55.     AVFrame *refframe;          // full decoded frame (without cursor)
  56.     AVFrame *jpgframe;          // decoded JPEG tile
  57.     uint8_t *tilebuffer;        // buffer containing tile data
  58.  
  59.     /* zlib interation */
  60.     uint8_t *deflatebuffer;
  61.     uLongf deflatelen;
  62.  
  63.     /* All that is cursor */
  64.     uint8_t    *cursor;
  65.     int        cursor_stride;
  66.     int        cursor_w, cursor_h, cursor_x, cursor_y;
  67.     int        cursor_hot_x, cursor_hot_y;
  68. } TDSCContext;
  69.  
  70. /* 1 byte bits, 1 byte planes, 2 bytes format (probably) */
  71. enum TDSCCursorFormat {
  72.     CUR_FMT_MONO = 0x01010004,
  73.     CUR_FMT_BGRA = 0x20010004,
  74.     CUR_FMT_RGBA = 0x20010008,
  75. };
  76.  
  77. static av_cold int tdsc_close(AVCodecContext *avctx)
  78. {
  79.     TDSCContext *ctx = avctx->priv_data;
  80.  
  81.     av_frame_free(&ctx->refframe);
  82.     av_frame_free(&ctx->jpgframe);
  83.     av_freep(&ctx->deflatebuffer);
  84.     av_freep(&ctx->tilebuffer);
  85.     av_freep(&ctx->cursor);
  86.     avcodec_free_context(&ctx->jpeg_avctx);
  87.  
  88.     return 0;
  89. }
  90.  
  91. static av_cold int tdsc_init(AVCodecContext *avctx)
  92. {
  93.     TDSCContext *ctx = avctx->priv_data;
  94.     const AVCodec *codec;
  95.     int ret;
  96.  
  97.     avctx->pix_fmt = AV_PIX_FMT_BGR24;
  98.  
  99.     /* These needs to be set to estimate buffer and frame size */
  100.     if (!(avctx->width && avctx->height)) {
  101.         av_log(avctx, AV_LOG_ERROR, "Video size not set.\n");
  102.         return AVERROR_INVALIDDATA;
  103.     }
  104.  
  105.     /* This value should be large enough for a RAW-only frame plus headers */
  106.     ctx->deflatelen = avctx->width * avctx->height * (3 + 1);
  107.     ret = av_reallocp(&ctx->deflatebuffer, ctx->deflatelen);
  108.     if (ret < 0)
  109.         return ret;
  110.  
  111.     /* Allocate reference and JPEG frame */
  112.     ctx->refframe = av_frame_alloc();
  113.     ctx->jpgframe = av_frame_alloc();
  114.     if (!ctx->refframe || !ctx->jpgframe)
  115.         return AVERROR(ENOMEM);
  116.  
  117.     /* Prepare everything needed for JPEG decoding */
  118.     codec = avcodec_find_decoder(AV_CODEC_ID_MJPEG);
  119.     if (!codec)
  120.         return AVERROR_BUG;
  121.     ctx->jpeg_avctx = avcodec_alloc_context3(codec);
  122.     if (!ctx->jpeg_avctx)
  123.         return AVERROR(ENOMEM);
  124.     ctx->jpeg_avctx->flags = avctx->flags;
  125.     ctx->jpeg_avctx->flags2 = avctx->flags2;
  126.     ctx->jpeg_avctx->dct_algo = avctx->dct_algo;
  127.     ctx->jpeg_avctx->idct_algo = avctx->idct_algo;
  128.     ret = ff_codec_open2_recursive(ctx->jpeg_avctx, codec, NULL);
  129.     if (ret < 0)
  130.         return ret;
  131.  
  132.     /* Set the output pixel format on the reference frame */
  133.     ctx->refframe->format = avctx->pix_fmt;
  134.  
  135.     return 0;
  136. }
  137.  
  138. #define APPLY_ALPHA(src, new, alpha) \
  139.     src = (src * (256 - alpha) + new * alpha) >> 8
  140.  
  141. /* Paint a region over a buffer, without drawing out of its bounds. */
  142. static void tdsc_paint_cursor(AVCodecContext *avctx, uint8_t *dst, int stride)
  143. {
  144.     TDSCContext *ctx = avctx->priv_data;
  145.     const uint8_t *cursor = ctx->cursor;
  146.     int x = ctx->cursor_x - ctx->cursor_hot_x;
  147.     int y = ctx->cursor_y - ctx->cursor_hot_y;
  148.     int w = ctx->cursor_w;
  149.     int h = ctx->cursor_h;
  150.     int i, j;
  151.  
  152.     if (!ctx->cursor)
  153.         return;
  154.  
  155.     if (x + w > ctx->width)
  156.         w = ctx->width - x;
  157.     if (y + h > ctx->height)
  158.         h = ctx->height - y;
  159.     if (x < 0) {
  160.         w      +=  x;
  161.         cursor += -x * 4;
  162.     } else {
  163.         dst    +=  x * 3;
  164.     }
  165.     if (y < 0) {
  166.         h      +=  y;
  167.         cursor += -y * ctx->cursor_stride;
  168.     } else {
  169.         dst    +=  y * stride;
  170.     }
  171.     if (w < 0 || h < 0)
  172.         return;
  173.  
  174.     for (j = 0; j < h; j++) {
  175.         for (i = 0; i < w; i++) {
  176.             uint8_t alpha = cursor[i * 4];
  177.             APPLY_ALPHA(dst[i * 3 + 0], cursor[i * 4 + 1], alpha);
  178.             APPLY_ALPHA(dst[i * 3 + 1], cursor[i * 4 + 2], alpha);
  179.             APPLY_ALPHA(dst[i * 3 + 2], cursor[i * 4 + 3], alpha);
  180.         }
  181.         dst    += stride;
  182.         cursor += ctx->cursor_stride;
  183.     }
  184. }
  185.  
  186. /* Load cursor data and store it in ABGR mode. */
  187. static int tdsc_load_cursor(AVCodecContext *avctx)
  188. {
  189.     TDSCContext *ctx  = avctx->priv_data;
  190.     int i, j, k, ret, bits, cursor_fmt;
  191.     uint8_t *dst;
  192.  
  193.     ctx->cursor_hot_x = bytestream2_get_le16(&ctx->gbc);
  194.     ctx->cursor_hot_y = bytestream2_get_le16(&ctx->gbc);
  195.     ctx->cursor_w     = bytestream2_get_le16(&ctx->gbc);
  196.     ctx->cursor_h     = bytestream2_get_le16(&ctx->gbc);
  197.  
  198.     ctx->cursor_stride = FFALIGN(ctx->cursor_w, 32) * 4;
  199.     cursor_fmt = bytestream2_get_le32(&ctx->gbc);
  200.  
  201.     if (ctx->cursor_x >= avctx->width || ctx->cursor_y >= avctx->height) {
  202.         av_log(avctx, AV_LOG_ERROR,
  203.                "Invalid cursor position (%d.%d outside %dx%d).\n",
  204.                ctx->cursor_x, ctx->cursor_y, avctx->width, avctx->height);
  205.         return AVERROR_INVALIDDATA;
  206.     }
  207.     if (ctx->cursor_w < 1 || ctx->cursor_w > 256 ||
  208.         ctx->cursor_h < 1 || ctx->cursor_h > 256) {
  209.         av_log(avctx, AV_LOG_ERROR,
  210.                "Invalid cursor dimensions %dx%d.\n",
  211.                ctx->cursor_w, ctx->cursor_h);
  212.         return AVERROR_INVALIDDATA;
  213.     }
  214.     if (ctx->cursor_hot_x > ctx->cursor_w ||
  215.         ctx->cursor_hot_y > ctx->cursor_h) {
  216.         av_log(avctx, AV_LOG_WARNING, "Invalid hotspot position %d.%d.\n",
  217.                ctx->cursor_hot_x, ctx->cursor_hot_y);
  218.         ctx->cursor_hot_x = FFMIN(ctx->cursor_hot_x, ctx->cursor_w - 1);
  219.         ctx->cursor_hot_y = FFMIN(ctx->cursor_hot_y, ctx->cursor_h - 1);
  220.     }
  221.  
  222.     ret = av_reallocp(&ctx->cursor, ctx->cursor_stride * ctx->cursor_h);
  223.     if (ret < 0) {
  224.         av_log(avctx, AV_LOG_ERROR, "Cannot allocate cursor buffer.\n");
  225.         return ret;
  226.     }
  227.  
  228.     dst = ctx->cursor;
  229.     /* here data is packed in BE */
  230.     switch (cursor_fmt) {
  231.     case CUR_FMT_MONO:
  232.         for (j = 0; j < ctx->cursor_h; j++) {
  233.             for (i = 0; i < ctx->cursor_w; i += 32) {
  234.                 bits = bytestream2_get_be32(&ctx->gbc);
  235.                 for (k = 0; k < 32; k++) {
  236.                     dst[0] = !!(bits & 0x80000000);
  237.                     dst   += 4;
  238.                     bits <<= 1;
  239.                 }
  240.             }
  241.             dst += ctx->cursor_stride - ctx->cursor_w * 4;
  242.         }
  243.  
  244.         dst = ctx->cursor;
  245.         for (j = 0; j < ctx->cursor_h; j++) {
  246.             for (i = 0; i < ctx->cursor_w; i += 32) {
  247.                 bits = bytestream2_get_be32(&ctx->gbc);
  248.                 for (k = 0; k < 32; k++) {
  249.                     int mask_bit = !!(bits & 0x80000000);
  250.                     switch (dst[0] * 2 + mask_bit) {
  251.                     case 0:
  252.                         dst[0] = 0xFF;
  253.                         dst[1] = 0x00;
  254.                         dst[2] = 0x00;
  255.                         dst[3] = 0x00;
  256.                         break;
  257.                     case 1:
  258.                         dst[0] = 0xFF;
  259.                         dst[1] = 0xFF;
  260.                         dst[2] = 0xFF;
  261.                         dst[3] = 0xFF;
  262.                         break;
  263.                     default:
  264.                         dst[0] = 0x00;
  265.                         dst[1] = 0x00;
  266.                         dst[2] = 0x00;
  267.                         dst[3] = 0x00;
  268.                     }
  269.                     dst   += 4;
  270.                     bits <<= 1;
  271.                 }
  272.             }
  273.             dst += ctx->cursor_stride - ctx->cursor_w * 4;
  274.         }
  275.         break;
  276.     case CUR_FMT_BGRA:
  277.     case CUR_FMT_RGBA:
  278.         /* Skip monochrome version of the cursor */
  279.         bytestream2_skip(&ctx->gbc,
  280.                          ctx->cursor_h * (FFALIGN(ctx->cursor_w, 32) >> 3));
  281.         if (cursor_fmt & 8) { // RGBA -> ABGR
  282.             for (j = 0; j < ctx->cursor_h; j++) {
  283.                 for (i = 0; i < ctx->cursor_w; i++) {
  284.                     int val = bytestream2_get_be32(&ctx->gbc);
  285.                     *dst++ = val >> 24;
  286.                     *dst++ = val >> 16;
  287.                     *dst++ = val >>  8;
  288.                     *dst++ = val >>  0;
  289.                 }
  290.                 dst += ctx->cursor_stride - ctx->cursor_w * 4;
  291.             }
  292.         } else { // BGRA -> ABGR
  293.             for (j = 0; j < ctx->cursor_h; j++) {
  294.                 for (i = 0; i < ctx->cursor_w; i++) {
  295.                     int val = bytestream2_get_be32(&ctx->gbc);
  296.                     *dst++ = val >>  0;
  297.                     *dst++ = val >> 24;
  298.                     *dst++ = val >> 16;
  299.                     *dst++ = val >>  8;
  300.                 }
  301.                 dst += ctx->cursor_stride - ctx->cursor_w * 4;
  302.             }
  303.         }
  304.         break;
  305.     default:
  306.         avpriv_request_sample(avctx, "Cursor format %08x", cursor_fmt);
  307.         return AVERROR_PATCHWELCOME;
  308.     }
  309.  
  310.     return 0;
  311. }
  312.  
  313. /* Convert a single YUV pixel to RGB. */
  314. static inline void tdsc_yuv2rgb(uint8_t *out, int Y, int U, int V)
  315. {
  316.     out[0] = av_clip_uint8(Y + (             91881 * V + 32768 >> 16));
  317.     out[1] = av_clip_uint8(Y + (-22554 * U - 46802 * V + 32768 >> 16));
  318.     out[2] = av_clip_uint8(Y + (116130 * U             + 32768 >> 16));
  319. }
  320.  
  321. /* Convert a YUV420 buffer to a RGB buffer. */
  322. static av_always_inline void tdsc_blit(uint8_t *dst, int dst_stride,
  323.                                        const uint8_t *srcy, int srcy_stride,
  324.                                        const uint8_t *srcu, const uint8_t *srcv,
  325.                                        int srcuv_stride, int width, int height)
  326. {
  327.     int col, line;
  328.     for (line = 0; line < height; line++) {
  329.         for (col = 0; col < width; col++)
  330.             tdsc_yuv2rgb(dst + col * 3, srcy[col],
  331.                          srcu[col >> 1] - 128, srcv[col >> 1] - 128);
  332.  
  333.         dst  +=   dst_stride;
  334.         srcy +=  srcy_stride;
  335.         srcu += srcuv_stride * (line & 1);
  336.         srcv += srcuv_stride * (line & 1);
  337.     }
  338. }
  339.  
  340. /* Invoke the MJPEG decoder to decode the tile. */
  341. static int tdsc_decode_jpeg_tile(AVCodecContext *avctx, int tile_size,
  342.                                  int x, int y, int w, int h)
  343. {
  344.     TDSCContext *ctx = avctx->priv_data;
  345.     AVPacket jpkt;
  346.     int got_frame = 0;
  347.     int ret;
  348.  
  349.     /* Prepare a packet and send to the MJPEG decoder */
  350.     av_init_packet(&jpkt);
  351.     jpkt.data = ctx->tilebuffer;
  352.     jpkt.size = tile_size;
  353.  
  354.     ret = avcodec_decode_video2(ctx->jpeg_avctx, ctx->jpgframe,
  355.                                 &got_frame, &jpkt);
  356.     if (ret < 0 || !got_frame || ctx->jpgframe->format != AV_PIX_FMT_YUVJ420P) {
  357.         av_log(avctx, AV_LOG_ERROR,
  358.                "JPEG decoding error (%d) for (%d) frame.\n",
  359.                ret, got_frame);
  360.  
  361.         /* Normally skip, error if explode */
  362.         if (avctx->err_recognition & AV_EF_EXPLODE)
  363.             return AVERROR_INVALIDDATA;
  364.         else
  365.             return 0;
  366.     }
  367.  
  368.     /* Let's paint ont the buffer */
  369.     tdsc_blit(ctx->refframe->data[0] + x * 3 + ctx->refframe->linesize[0] * y,
  370.               ctx->refframe->linesize[0],
  371.               ctx->jpgframe->data[0], ctx->jpgframe->linesize[0],
  372.               ctx->jpgframe->data[1], ctx->jpgframe->data[2],
  373.               ctx->jpgframe->linesize[1], w, h);
  374.  
  375.     av_frame_unref(ctx->jpgframe);
  376.  
  377.     return 0;
  378. }
  379.  
  380. /* Parse frame and either copy data or decode JPEG. */
  381. static int tdsc_decode_tiles(AVCodecContext *avctx, int number_tiles)
  382. {
  383.     TDSCContext *ctx = avctx->priv_data;
  384.     int i;
  385.  
  386.     /* Iterate over the number of tiles */
  387.     for (i = 0; i < number_tiles; i++) {
  388.         int tile_size;
  389.         int tile_mode;
  390.         int x, y, w, h;
  391.         int ret;
  392.  
  393.         if (bytestream2_get_bytes_left(&ctx->gbc) < 4 ||
  394.             bytestream2_get_le32(&ctx->gbc) != MKTAG('T','D','S','B') ||
  395.             bytestream2_get_bytes_left(&ctx->gbc) < TDSB_HEADER_SIZE - 4) {
  396.             av_log(avctx, AV_LOG_ERROR, "TDSB tag is too small.\n");
  397.             return AVERROR_INVALIDDATA;
  398.         }
  399.  
  400.         tile_size = bytestream2_get_le32(&ctx->gbc);
  401.         if (bytestream2_get_bytes_left(&ctx->gbc) < tile_size)
  402.             return AVERROR_INVALIDDATA;
  403.  
  404.         tile_mode = bytestream2_get_le32(&ctx->gbc);
  405.         bytestream2_skip(&ctx->gbc, 4); // unknown
  406.         x = bytestream2_get_le32(&ctx->gbc);
  407.         y = bytestream2_get_le32(&ctx->gbc);
  408.         w = bytestream2_get_le32(&ctx->gbc) - x;
  409.         h = bytestream2_get_le32(&ctx->gbc) - y;
  410.  
  411.         if (x >= ctx->width || y >= ctx->height) {
  412.             av_log(avctx, AV_LOG_ERROR,
  413.                    "Invalid tile position (%d.%d outside %dx%d).\n",
  414.                    x, y, ctx->width, ctx->height);
  415.             return AVERROR_INVALIDDATA;
  416.         }
  417.         if (x + w > ctx->width || y + h > ctx->height) {
  418.             av_log(avctx, AV_LOG_ERROR,
  419.                    "Invalid tile size %dx%d\n", w, h);
  420.             return AVERROR_INVALIDDATA;
  421.         }
  422.  
  423.         ret = av_reallocp(&ctx->tilebuffer, tile_size);
  424.         if (!ctx->tilebuffer)
  425.             return ret;
  426.  
  427.         bytestream2_get_buffer(&ctx->gbc, ctx->tilebuffer, tile_size);
  428.  
  429.         if (tile_mode == MKTAG('G','E','P','J')) {
  430.             /* Decode JPEG tile and copy it in the reference frame */
  431.             ret = tdsc_decode_jpeg_tile(avctx, tile_size, x, y, w, h);
  432.             if (ret < 0)
  433.                 return ret;
  434.         } else if (tile_mode == MKTAG(' ','W','A','R')) {
  435.             /* Just copy the buffer to output */
  436.             av_image_copy_plane(ctx->refframe->data[0] + x * 3 +
  437.                                 ctx->refframe->linesize[0] * y,
  438.                                 ctx->refframe->linesize[0], ctx->tilebuffer,
  439.                                 w * 3, w * 3, h);
  440.         } else {
  441.             av_log(avctx, AV_LOG_ERROR, "Unknown tile type %08x.\n", tile_mode);
  442.             return AVERROR_INVALIDDATA;
  443.         }
  444.         av_log(avctx, AV_LOG_DEBUG, "Tile %d, %dx%d (%d.%d)\n", i, w, h, x, y);
  445.     }
  446.  
  447.     return 0;
  448. }
  449.  
  450. static int tdsc_parse_tdsf(AVCodecContext *avctx, int number_tiles)
  451. {
  452.     TDSCContext *ctx = avctx->priv_data;
  453.     int ret, w, h, init_refframe = !ctx->refframe->data[0];
  454.  
  455.     /* BITMAPINFOHEADER
  456.      * http://msdn.microsoft.com/en-us/library/windows/desktop/dd183376.aspx */
  457.     if (bytestream2_get_le32(&ctx->gbc) != BITMAPINFOHEADER_SIZE)
  458.         return AVERROR_INVALIDDATA;
  459.  
  460.     /* Store size, but wait for context reinit before updating avctx */
  461.     w =  bytestream2_get_le32(&ctx->gbc);
  462.     h = -bytestream2_get_le32(&ctx->gbc);
  463.  
  464.     if (bytestream2_get_le16(&ctx->gbc) != 1 ||  // 1 plane
  465.         bytestream2_get_le16(&ctx->gbc) != 24)   // BGR24
  466.         return AVERROR_INVALIDDATA;
  467.  
  468.     bytestream2_skip(&ctx->gbc, 24); // unused fields
  469.  
  470.     /* Update sizes */
  471.     if (avctx->width != w || avctx->height != h) {
  472.         av_log(avctx, AV_LOG_DEBUG, "Size update %dx%d -> %d%d.\n",
  473.                avctx->width, avctx->height, ctx->width, ctx->height);
  474.         ret = ff_set_dimensions(avctx, w, h);
  475.         if (ret < 0)
  476.             return ret;
  477.         init_refframe = 1;
  478.     }
  479.     ctx->refframe->width  = ctx->width  = w;
  480.     ctx->refframe->height = ctx->height = h;
  481.  
  482.     /* Allocate the reference frame if not already done or on size change */
  483.     if (init_refframe) {
  484.         ret = av_frame_get_buffer(ctx->refframe, 32);
  485.         if (ret < 0)
  486.             return ret;
  487.     }
  488.  
  489.     /* Decode all tiles in a frame */
  490.     return tdsc_decode_tiles(avctx, number_tiles);
  491. }
  492.  
  493. static int tdsc_parse_dtsm(AVCodecContext *avctx)
  494. {
  495.     TDSCContext *ctx = avctx->priv_data;
  496.     int ret;
  497.     int action = bytestream2_get_le32(&ctx->gbc);
  498.  
  499.     bytestream2_skip(&ctx->gbc, 4); // some kind of ID or version maybe?
  500.  
  501.     if (action == 2 || action == 3) {
  502.         /* Load cursor coordinates */
  503.         ctx->cursor_x = bytestream2_get_le32(&ctx->gbc);
  504.         ctx->cursor_y = bytestream2_get_le32(&ctx->gbc);
  505.  
  506.         /* Load a full cursor sprite */
  507.         if (action == 3) {
  508.             ret = tdsc_load_cursor(avctx);
  509.             /* Do not consider cursor errors fatal unless in explode mode */
  510.             if (ret < 0 && (avctx->err_recognition & AV_EF_EXPLODE))
  511.                 return ret;
  512.         }
  513.     } else {
  514.         avpriv_request_sample(avctx, "Cursor action %d", action);
  515.     }
  516.  
  517.     return 0;
  518. }
  519.  
  520. static int tdsc_decode_frame(AVCodecContext *avctx, void *data,
  521.                              int *got_frame, AVPacket *avpkt)
  522. {
  523.     TDSCContext *ctx = avctx->priv_data;
  524.     AVFrame *frame = data;
  525.     int ret, tag_header, keyframe = 0;
  526.     uLongf dlen;
  527.  
  528.     /* Resize deflate buffer on resolution change */
  529.     if (ctx->width != avctx->width || ctx->height != avctx->height) {
  530.         ctx->deflatelen = avctx->width * avctx->height * (3 + 1);
  531.         ret = av_reallocp(&ctx->deflatebuffer, ctx->deflatelen);
  532.         if (ret < 0)
  533.             return ret;
  534.     }
  535.     dlen = ctx->deflatelen;
  536.  
  537.     /* Frames are deflated, need to inflate them first */
  538.     ret = uncompress(ctx->deflatebuffer, &dlen, avpkt->data, avpkt->size);
  539.     if (ret) {
  540.         av_log(avctx, AV_LOG_ERROR, "Deflate error %d.\n", ret);
  541.         return AVERROR_UNKNOWN;
  542.     }
  543.  
  544.     bytestream2_init(&ctx->gbc, ctx->deflatebuffer, dlen);
  545.  
  546.     /* Check for tag and for size info */
  547.     if (bytestream2_get_bytes_left(&ctx->gbc) < 4 + 4) {
  548.         av_log(avctx, AV_LOG_ERROR, "Frame is too small.\n");
  549.         return AVERROR_INVALIDDATA;
  550.     }
  551.  
  552.     /* Read tag */
  553.     tag_header = bytestream2_get_le32(&ctx->gbc);
  554.  
  555.     if (tag_header == MKTAG('T','D','S','F')) {
  556.         int number_tiles;
  557.         if (bytestream2_get_bytes_left(&ctx->gbc) < TDSF_HEADER_SIZE) {
  558.             av_log(avctx, AV_LOG_ERROR, "TDSF tag is too small.\n");
  559.             return AVERROR_INVALIDDATA;
  560.         }
  561.         /* First 4 bytes here are the number of GEPJ/WAR tiles in this frame */
  562.         number_tiles = bytestream2_get_le32(&ctx->gbc);
  563.  
  564.         bytestream2_skip(&ctx->gbc, 4); // internal timestamp maybe?
  565.         keyframe = bytestream2_get_le32(&ctx->gbc) == 0x30;
  566.  
  567.         ret = tdsc_parse_tdsf(avctx, number_tiles);
  568.         if (ret < 0)
  569.             return ret;
  570.  
  571.         /* Check if there is anything else we are able to parse */
  572.         if (bytestream2_get_bytes_left(&ctx->gbc) >= 4 + 4)
  573.             tag_header = bytestream2_get_le32(&ctx->gbc);
  574.     }
  575.  
  576.     /* This tag can be after a TDSF block or on its own frame */
  577.     if (tag_header == MKTAG('D','T','S','M')) {
  578.         /* First 4 bytes here are the total size in bytes for this frame */
  579.         int tag_size = bytestream2_get_le32(&ctx->gbc);
  580.  
  581.         if (bytestream2_get_bytes_left(&ctx->gbc) < tag_size) {
  582.             av_log(avctx, AV_LOG_ERROR, "DTSM tag is too small.\n");
  583.             return AVERROR_INVALIDDATA;
  584.         }
  585.  
  586.         ret = tdsc_parse_dtsm(avctx);
  587.         if (ret < 0)
  588.             return ret;
  589.     }
  590.  
  591.     /* Get the output frame and copy the reference frame */
  592.     ret = ff_get_buffer(avctx, frame, 0);
  593.     if (ret < 0)
  594.         return ret;
  595.  
  596.     ret = av_frame_copy(frame, ctx->refframe);
  597.     if (ret < 0)
  598.         return ret;
  599.  
  600.     /* Paint the cursor on the output frame */
  601.     tdsc_paint_cursor(avctx, frame->data[0], frame->linesize[0]);
  602.  
  603.     /* Frame is ready to be output */
  604.     if (keyframe) {
  605.         frame->pict_type = AV_PICTURE_TYPE_I;
  606.         frame->key_frame = 1;
  607.     } else {
  608.         frame->pict_type = AV_PICTURE_TYPE_P;
  609.     }
  610.     *got_frame = 1;
  611.  
  612.     return 0;
  613. }
  614.  
  615. AVCodec ff_tdsc_decoder = {
  616.     .name           = "tdsc",
  617.     .long_name      = NULL_IF_CONFIG_SMALL("TDSC"),
  618.     .type           = AVMEDIA_TYPE_VIDEO,
  619.     .id             = AV_CODEC_ID_TDSC,
  620.     .init           = tdsc_init,
  621.     .decode         = tdsc_decode_frame,
  622.     .close          = tdsc_close,
  623.     .priv_data_size = sizeof(TDSCContext),
  624.     .capabilities   = AV_CODEC_CAP_DR1,
  625.     .caps_internal  = FF_CODEC_CAP_INIT_THREADSAFE |
  626.                       FF_CODEC_CAP_INIT_CLEANUP,
  627. };
  628.