/*
 * huffyuv decoder
 *
 * Copyright (c) 2002-2003 Michael Niedermayer <michaelni@gmx.at>
 *
 * see http://www.pcisys.net/~melanson/codecs/huffyuv.txt for a description of
 * the algorithm used
 *
 * This file is part of FFmpeg.
 *
 * FFmpeg is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * FFmpeg is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with FFmpeg; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
 */

/**
 * @file
 * huffyuv decoder
 */

#include "avcodec.h"
#include "get_bits.h"
#include "huffyuv.h"
#include "thread.h"

#define classic_shift_luma_table_size 42
static const unsigned char classic_shift_luma[classic_shift_luma_table_size + FF_INPUT_BUFFER_PADDING_SIZE] = {
  34,36,35,69,135,232,9,16,10,24,11,23,12,16,13,10,14,8,15,8,
  16,8,17,20,16,10,207,206,205,236,11,8,10,21,9,23,8,8,199,70,
  69,68, 0,
  0,0,0,0,0,0,0,0,
};

#define classic_shift_chroma_table_size 59
static const unsigned char classic_shift_chroma[classic_shift_chroma_table_size + FF_INPUT_BUFFER_PADDING_SIZE] = {
  66,36,37,38,39,40,41,75,76,77,110,239,144,81,82,83,84,85,118,183,
  56,57,88,89,56,89,154,57,58,57,26,141,57,56,58,57,58,57,184,119,
  214,245,116,83,82,49,80,79,78,77,44,75,41,40,39,38,37,36,34, 0,
  0,0,0,0,0,0,0,0,
};

static const unsigned char classic_add_luma[256] = {
    3,  9,  5, 12, 10, 35, 32, 29, 27, 50, 48, 45, 44, 41, 39, 37,
   73, 70, 68, 65, 64, 61, 58, 56, 53, 50, 49, 46, 44, 41, 38, 36,
   68, 65, 63, 61, 58, 55, 53, 51, 48, 46, 45, 43, 41, 39, 38, 36,
   35, 33, 32, 30, 29, 27, 26, 25, 48, 47, 46, 44, 43, 41, 40, 39,
   37, 36, 35, 34, 32, 31, 30, 28, 27, 26, 24, 23, 22, 20, 19, 37,
   35, 34, 33, 31, 30, 29, 27, 26, 24, 23, 21, 20, 18, 17, 15, 29,
   27, 26, 24, 22, 21, 19, 17, 16, 14, 26, 25, 23, 21, 19, 18, 16,
   15, 27, 25, 23, 21, 19, 17, 16, 14, 26, 25, 23, 21, 18, 17, 14,
   12, 17, 19, 13,  4,  9,  2, 11,  1,  7,  8,  0, 16,  3, 14,  6,
   12, 10,  5, 15, 18, 11, 10, 13, 15, 16, 19, 20, 22, 24, 27, 15,
   18, 20, 22, 24, 26, 14, 17, 20, 22, 24, 27, 15, 18, 20, 23, 25,
   28, 16, 19, 22, 25, 28, 32, 36, 21, 25, 29, 33, 38, 42, 45, 49,
   28, 31, 34, 37, 40, 42, 44, 47, 49, 50, 52, 54, 56, 57, 59, 60,
   62, 64, 66, 67, 69, 35, 37, 39, 40, 42, 43, 45, 47, 48, 51, 52,
   54, 55, 57, 59, 60, 62, 63, 66, 67, 69, 71, 72, 38, 40, 42, 43,
   46, 47, 49, 51, 26, 28, 30, 31, 33, 34, 18, 19, 11, 13,  7,  8,
};

static const unsigned char classic_add_chroma[256] = {
    3,  1,  2,  2,  2,  2,  3,  3,  7,  5,  7,  5,  8,  6, 11,  9,
    7, 13, 11, 10,  9,  8,  7,  5,  9,  7,  6,  4,  7,  5,  8,  7,
   11,  8, 13, 11, 19, 15, 22, 23, 20, 33, 32, 28, 27, 29, 51, 77,
   43, 45, 76, 81, 46, 82, 75, 55, 56,144, 58, 80, 60, 74,147, 63,
  143, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79,
   80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 27, 30, 21, 22,
   17, 14,  5,  6,100, 54, 47, 50, 51, 53,106,107,108,109,110,111,
  112,113,114,115,  4,117,118, 92, 94,121,122,  3,124,103,  2,  1,
    0,129,130,131,120,119,126,125,136,137,138,139,140,141,142,134,
  135,132,133,104, 64,101, 62, 57,102, 95, 93, 59, 61, 28, 97, 96,
   52, 49, 48, 29, 32, 25, 24, 46, 23, 98, 45, 44, 43, 20, 42, 41,
   19, 18, 99, 40, 15, 39, 38, 16, 13, 12, 11, 37, 10,  9,  8, 36,
    7,128,127,105,123,116, 35, 34, 33,145, 31, 79, 42,146, 78, 26,
   83, 48, 49, 50, 44, 47, 26, 31, 30, 18, 17, 19, 21, 24, 25, 13,
   14, 16, 17, 18, 20, 21, 12, 14, 15,  9, 10,  6,  9,  6,  5,  8,
    6, 12,  8, 10,  7,  9,  6,  4,  6,  2,  2,  3,  3,  3,  3,  2,
};

static int read_len_table(uint8_t *dst, GetBitContext *gb)
{
    int i, val, repeat;

    for (i = 0; i < 256;) {
        repeat = get_bits(gb, 3);
        val    = get_bits(gb, 5);
        if (repeat == 0)
            repeat = get_bits(gb, 8);
        if (i + repeat > 256 || get_bits_left(gb) < 0) {
            av_log(NULL, AV_LOG_ERROR, "Error reading huffman table\n");
            return -1;
        }
        while (repeat--)
            dst[i++] = val;
    }
    return 0;
}

static int generate_joint_tables(HYuvContext *s)
{
    uint16_t symbols[1 << VLC_BITS];
    uint16_t bits[1 << VLC_BITS];
    uint8_t len[1 << VLC_BITS];
    int ret;

    if (s->bitstream_bpp < 24) {
        int p, i, y, u;
        for (p = 0; p < 3; p++) {
            for (i = y = 0; y < 256; y++) {
                int len0 = s->len[0][y];
                int limit = VLC_BITS - len0;
                if(limit <= 0 || !len0)
                    continue;
                for (u = 0; u < 256; u++) {
                    int len1 = s->len[p][u];
                    if (len1 > limit || !len1)
                        continue;
                    av_assert0(i < (1 << VLC_BITS));
                    len[i] = len0 + len1;
                    bits[i] = (s->bits[0][y] << len1) + s->bits[p][u];
                    symbols[i] = (y << 8) + u;
                    if(symbols[i] != 0xffff) // reserved to mean "invalid"
                        i++;
                }
            }
            ff_free_vlc(&s->vlc[3 + p]);
            if ((ret = ff_init_vlc_sparse(&s->vlc[3 + p], VLC_BITS, i, len, 1, 1,
                                          bits, 2, 2, symbols, 2, 2, 0)) < 0)
                return ret;
        }
    } else {
        uint8_t (*map)[4] = (uint8_t(*)[4])s->pix_bgr_map;
        int i, b, g, r, code;
        int p0 = s->decorrelate;
        int p1 = !s->decorrelate;
        // restrict the range to +/-16 because that's pretty much guaranteed to
        // cover all the combinations that fit in 11 bits total, and it doesn't
        // matter if we miss a few rare codes.
        for (i = 0, g = -16; g < 16; g++) {
            int len0 = s->len[p0][g & 255];
            int limit0 = VLC_BITS - len0;
            if (limit0 < 2 || !len0)
                continue;
            for (b = -16; b < 16; b++) {
                int len1 = s->len[p1][b & 255];
                int limit1 = limit0 - len1;
                if (limit1 < 1 || !len1)
                    continue;
                code = (s->bits[p0][g & 255] << len1) + s->bits[p1][b & 255];
                for (r = -16; r < 16; r++) {
                    int len2 = s->len[2][r & 255];
                    if (len2 > limit1 || !len2)
                        continue;
                    av_assert0(i < (1 << VLC_BITS));
                    len[i] = len0 + len1 + len2;
                    bits[i] = (code << len2) + s->bits[2][r & 255];
                    if (s->decorrelate) {
                        map[i][G] = g;
                        map[i][B] = g + b;
                        map[i][R] = g + r;
                    } else {
                        map[i][B] = g;
                        map[i][G] = b;
                        map[i][R] = r;
                    }
                    i++;
                }
            }
        }
        ff_free_vlc(&s->vlc[3]);
        if ((ret = init_vlc(&s->vlc[3], VLC_BITS, i, len, 1, 1, bits, 2, 2, 0)) < 0)
            return ret;
    }
    return 0;
}

static int read_huffman_tables(HYuvContext *s, const uint8_t *src, int length)
{
    GetBitContext gb;
    int i;
    int ret;

    init_get_bits(&gb, src, length * 8);

    for (i = 0; i < 3; i++) {
        if (read_len_table(s->len[i], &gb) < 0)
            return -1;
        if (ff_huffyuv_generate_bits_table(s->bits[i], s->len[i]) < 0) {
            return -1;
        }
        ff_free_vlc(&s->vlc[i]);
        if ((ret = init_vlc(&s->vlc[i], VLC_BITS, 256, s->len[i], 1, 1,
                           s->bits[i], 4, 4, 0)) < 0)
            return ret;
    }

    if ((ret = generate_joint_tables(s)) < 0)
        return ret;

    return (get_bits_count(&gb) + 7) / 8;
}

static int read_old_huffman_tables(HYuvContext *s)
{
    GetBitContext gb;
    int i;
    int ret;

    init_get_bits(&gb, classic_shift_luma,
                  classic_shift_luma_table_size * 8);
    if (read_len_table(s->len[0], &gb) < 0)
        return -1;

    init_get_bits(&gb, classic_shift_chroma,
                  classic_shift_chroma_table_size * 8);
    if (read_len_table(s->len[1], &gb) < 0)
        return -1;

    for(i=0; i<256; i++) s->bits[0][i] = classic_add_luma  [i];
    for(i=0; i<256; i++) s->bits[1][i] = classic_add_chroma[i];

    if (s->bitstream_bpp >= 24) {
        memcpy(s->bits[1], s->bits[0], 256 * sizeof(uint32_t));
        memcpy(s->len[1] , s->len [0], 256 * sizeof(uint8_t));
    }
    memcpy(s->bits[2], s->bits[1], 256 * sizeof(uint32_t));
    memcpy(s->len[2] , s->len [1], 256 * sizeof(uint8_t));

    for (i = 0; i < 3; i++) {
        ff_free_vlc(&s->vlc[i]);
        if ((ret = init_vlc(&s->vlc[i], VLC_BITS, 256, s->len[i], 1, 1,
                            s->bits[i], 4, 4, 0)) < 0)
            return ret;
    }

    if ((ret = generate_joint_tables(s)) < 0)
        return ret;

    return 0;
}

static av_cold int decode_init(AVCodecContext *avctx)
{
    HYuvContext *s = avctx->priv_data;

    ff_huffyuv_common_init(avctx);
    memset(s->vlc, 0, 3 * sizeof(VLC));

    avcodec_get_frame_defaults(&s->picture);
    s->interlaced = s->height > 288;

    s->bgr32 = 1;

    if (avctx->extradata_size) {
        if ((avctx->bits_per_coded_sample & 7) &&
            avctx->bits_per_coded_sample != 12)
            s->version = 1; // do such files exist at all?
        else
            s->version = 2;
    } else
        s->version = 0;

    if (s->version == 2) {
        int method, interlace;

        if (avctx->extradata_size < 4)
            return -1;

        method = ((uint8_t*)avctx->extradata)[0];
        s->decorrelate = method & 64 ? 1 : 0;
        s->predictor = method & 63;
        s->bitstream_bpp = ((uint8_t*)avctx->extradata)[1];
        if (s->bitstream_bpp == 0)
            s->bitstream_bpp = avctx->bits_per_coded_sample & ~7;
        interlace = (((uint8_t*)avctx->extradata)[2] & 0x30) >> 4;
        s->interlaced = (interlace == 1) ? 1 : (interlace == 2) ? 0 : s->interlaced;
        s->context = ((uint8_t*)avctx->extradata)[2] & 0x40 ? 1 : 0;

        if ( read_huffman_tables(s, ((uint8_t*)avctx->extradata) + 4,
                                 avctx->extradata_size - 4) < 0)
            return AVERROR_INVALIDDATA;
    }else{
        switch (avctx->bits_per_coded_sample & 7) {
        case 1:
            s->predictor = LEFT;
            s->decorrelate = 0;
            break;
        case 2:
            s->predictor = LEFT;
            s->decorrelate = 1;
            break;
        case 3:
            s->predictor = PLANE;
            s->decorrelate = avctx->bits_per_coded_sample >= 24;
            break;
        case 4:
            s->predictor = MEDIAN;
            s->decorrelate = 0;
            break;
        default:
            s->predictor = LEFT; //OLD
            s->decorrelate = 0;
            break;
        }
        s->bitstream_bpp = avctx->bits_per_coded_sample & ~7;
        s->context = 0;

        if (read_old_huffman_tables(s) < 0)
            return AVERROR_INVALIDDATA;
    }

    switch (s->bitstream_bpp) {
    case 12:
        avctx->pix_fmt = AV_PIX_FMT_YUV420P;
        break;
    case 16:
        if (s->yuy2) {
            avctx->pix_fmt = AV_PIX_FMT_YUYV422;
        } else {
            avctx->pix_fmt = AV_PIX_FMT_YUV422P;
        }
        break;
    case 24:
    case 32:
        if (s->bgr32) {
            avctx->pix_fmt = AV_PIX_FMT_RGB32;
        } else {
            avctx->pix_fmt = AV_PIX_FMT_BGR24;
        }
        break;
    default:
        return AVERROR_INVALIDDATA;
    }

    if ((avctx->pix_fmt == AV_PIX_FMT_YUV422P || avctx->pix_fmt == AV_PIX_FMT_YUV420P) && avctx->width & 1) {
        av_log(avctx, AV_LOG_ERROR, "width must be even for this colorspace\n");
        return AVERROR_INVALIDDATA;
    }
    if (s->predictor == MEDIAN && avctx->pix_fmt == AV_PIX_FMT_YUV422P && avctx->width%4) {
        av_log(avctx, AV_LOG_ERROR, "width must be a multiple of 4 this colorspace and predictor\n");
        return AVERROR_INVALIDDATA;
    }
    if (ff_huffyuv_alloc_temp(s)) {
        ff_huffyuv_common_end(s);
        return AVERROR(ENOMEM);
    }

    return 0;
}

static av_cold int decode_init_thread_copy(AVCodecContext *avctx)
{
    HYuvContext *s = avctx->priv_data;
    int i;

    if (ff_huffyuv_alloc_temp(s)) {
        ff_huffyuv_common_end(s);
        return AVERROR(ENOMEM);
    }

    for (i = 0; i < 6; i++)
        s->vlc[i].table = NULL;

    if (s->version == 2) {
        if (read_huffman_tables(s, ((uint8_t*)avctx->extradata) + 4,
                                avctx->extradata_size) < 0)
            return AVERROR_INVALIDDATA;
    } else {
        if (read_old_huffman_tables(s) < 0)
            return AVERROR_INVALIDDATA;
    }

    return 0;
}

/* TODO instead of restarting the read when the code isn't in the first level
 * of the joint table, jump into the 2nd level of the individual table. */
#define READ_2PIX(dst0, dst1, plane1){\
    uint16_t code = get_vlc2(&s->gb, s->vlc[3+plane1].table, VLC_BITS, 1);\
    if(code != 0xffff){\
        dst0 = code>>8;\
        dst1 = code;\
    }else{\
        dst0 = get_vlc2(&s->gb, s->vlc[0].table, VLC_BITS, 3);\
        dst1 = get_vlc2(&s->gb, s->vlc[plane1].table, VLC_BITS, 3);\
    }\
}

static void decode_422_bitstream(HYuvContext *s, int count)
{
    int i;

    count /= 2;

    if (count >= (get_bits_left(&s->gb)) / (31 * 4)) {
        for (i = 0; i < count && get_bits_left(&s->gb) > 0; i++) {
            READ_2PIX(s->temp[0][2 * i    ], s->temp[1][i], 1);
            READ_2PIX(s->temp[0][2 * i + 1], s->temp[2][i], 2);
        }
    } else {
        for (i = 0; i < count; i++) {
            READ_2PIX(s->temp[0][2 * i    ], s->temp[1][i], 1);
            READ_2PIX(s->temp[0][2 * i + 1], s->temp[2][i], 2);
        }
    }
}

static void decode_gray_bitstream(HYuvContext *s, int count)
{
    int i;

    count/=2;

    if (count >= (get_bits_left(&s->gb)) / (31 * 2)) {
        for (i = 0; i < count && get_bits_left(&s->gb) > 0; i++) {
            READ_2PIX(s->temp[0][2 * i], s->temp[0][2 * i + 1], 0);
        }
    } else {
        for(i=0; i<count; i++){
            READ_2PIX(s->temp[0][2 * i], s->temp[0][2 * i + 1], 0);
        }
    }
}

static av_always_inline void decode_bgr_1(HYuvContext *s, int count,
                                          int decorrelate, int alpha)
{
    int i;
    for (i = 0; i < count; i++) {
        int code = get_vlc2(&s->gb, s->vlc[3].table, VLC_BITS, 1);
        if (code != -1) {
            *(uint32_t*)&s->temp[0][4 * i] = s->pix_bgr_map[code];
        } else if(decorrelate) {
            s->temp[0][4 * i + G] = get_vlc2(&s->gb, s->vlc[1].table, VLC_BITS, 3);
            s->temp[0][4 * i + B] = get_vlc2(&s->gb, s->vlc[0].table, VLC_BITS, 3) +
                                    s->temp[0][4 * i + G];
            s->temp[0][4 * i + R] = get_vlc2(&s->gb, s->vlc[2].table, VLC_BITS, 3) +
                                    s->temp[0][4 * i + G];
        } else {
            s->temp[0][4 * i + B] = get_vlc2(&s->gb, s->vlc[0].table, VLC_BITS, 3);
            s->temp[0][4 * i + G] = get_vlc2(&s->gb, s->vlc[1].table, VLC_BITS, 3);
            s->temp[0][4 * i + R] = get_vlc2(&s->gb, s->vlc[2].table, VLC_BITS, 3);
        }
        if (alpha)
            s->temp[0][4 * i + A] = get_vlc2(&s->gb, s->vlc[2].table, VLC_BITS, 3);
    }
}

static void decode_bgr_bitstream(HYuvContext *s, int count)
{
    if (s->decorrelate) {
        if (s->bitstream_bpp==24)
            decode_bgr_1(s, count, 1, 0);
        else
            decode_bgr_1(s, count, 1, 1);
    } else {
        if (s->bitstream_bpp==24)
            decode_bgr_1(s, count, 0, 0);
        else
            decode_bgr_1(s, count, 0, 1);
    }
}

static void draw_slice(HYuvContext *s, AVFrame *frame, int y)
{
    int h, cy, i;
    int offset[AV_NUM_DATA_POINTERS];

    if (s->avctx->draw_horiz_band==NULL)
        return;

    h = y - s->last_slice_end;
    y -= h;

    if (s->bitstream_bpp == 12) {
        cy = y>>1;
    } else {
        cy = y;
    }

    offset[0] = frame->linesize[0] * y;
    offset[1] = frame->linesize[1] * cy;
    offset[2] = frame->linesize[2] * cy;
    for (i = 3; i < AV_NUM_DATA_POINTERS; i++)
        offset[i] = 0;
    emms_c();

    s->avctx->draw_horiz_band(s->avctx, frame, offset, y, 3, h);

    s->last_slice_end = y + h;
}

static int decode_frame(AVCodecContext *avctx, void *data, int *got_frame,
                        AVPacket *avpkt)
{
    const uint8_t *buf = avpkt->data;
    int buf_size = avpkt->size;
    HYuvContext *s = avctx->priv_data;
    const int width = s->width;
    const int width2 = s->width>>1;
    const int height = s->height;
    int fake_ystride, fake_ustride, fake_vstride;
    ThreadFrame frame = { .f = data };
    AVFrame * const p = data;
    int table_size = 0, ret;

    av_fast_padded_malloc(&s->bitstream_buffer,
                   &s->bitstream_buffer_size,
                   buf_size);
    if (!s->bitstream_buffer)
        return AVERROR(ENOMEM);

    s->dsp.bswap_buf((uint32_t*)s->bitstream_buffer,
                     (const uint32_t*)buf, buf_size / 4);

    if ((ret = ff_thread_get_buffer(avctx, &frame, 0)) < 0)
        return ret;

    if (s->context) {
        table_size = read_huffman_tables(s, s->bitstream_buffer, buf_size);
        if (table_size < 0)
            return AVERROR_INVALIDDATA;
    }

    if ((unsigned)(buf_size-table_size) >= INT_MAX / 8)
        return AVERROR_INVALIDDATA;

    init_get_bits(&s->gb, s->bitstream_buffer+table_size,
                  (buf_size-table_size) * 8);

    fake_ystride = s->interlaced ? p->linesize[0] * 2  : p->linesize[0];
    fake_ustride = s->interlaced ? p->linesize[1] * 2  : p->linesize[1];
    fake_vstride = s->interlaced ? p->linesize[2] * 2  : p->linesize[2];

    s->last_slice_end = 0;

    if (s->bitstream_bpp < 24) {
        int y, cy;
        int lefty, leftu, leftv;
        int lefttopy, lefttopu, lefttopv;

        if (s->yuy2) {
            p->data[0][3] = get_bits(&s->gb, 8);
            p->data[0][2] = get_bits(&s->gb, 8);
            p->data[0][1] = get_bits(&s->gb, 8);
            p->data[0][0] = get_bits(&s->gb, 8);

            av_log(avctx, AV_LOG_ERROR,
                   "YUY2 output is not implemented yet\n");
            return AVERROR_PATCHWELCOME;
        } else {

            leftv = p->data[2][0] = get_bits(&s->gb, 8);
            lefty = p->data[0][1] = get_bits(&s->gb, 8);
            leftu = p->data[1][0] = get_bits(&s->gb, 8);
                    p->data[0][0] = get_bits(&s->gb, 8);

            switch (s->predictor) {
            case LEFT:
            case PLANE:
                decode_422_bitstream(s, width-2);
                lefty = s->dsp.add_hfyu_left_prediction(p->data[0] + 2, s->temp[0], width-2, lefty);
                if (!(s->flags&CODEC_FLAG_GRAY)) {
                    leftu = s->dsp.add_hfyu_left_prediction(p->data[1] + 1, s->temp[1], width2 - 1, leftu);
                    leftv = s->dsp.add_hfyu_left_prediction(p->data[2] + 1, s->temp[2], width2 - 1, leftv);
                }

                for (cy = y = 1; y < s->height; y++, cy++) {
                    uint8_t *ydst, *udst, *vdst;

                    if (s->bitstream_bpp == 12) {
                        decode_gray_bitstream(s, width);

                        ydst = p->data[0] + p->linesize[0] * y;

                        lefty = s->dsp.add_hfyu_left_prediction(ydst, s->temp[0], width, lefty);
                        if (s->predictor == PLANE) {
                            if (y > s->interlaced)
                                s->dsp.add_bytes(ydst, ydst - fake_ystride, width);
                        }
                        y++;
                        if (y >= s->height) break;
                    }

                    draw_slice(s, p, y);

                    ydst = p->data[0] + p->linesize[0]*y;
                    udst = p->data[1] + p->linesize[1]*cy;
                    vdst = p->data[2] + p->linesize[2]*cy;

                    decode_422_bitstream(s, width);
                    lefty = s->dsp.add_hfyu_left_prediction(ydst, s->temp[0], width, lefty);
                    if (!(s->flags & CODEC_FLAG_GRAY)) {
                        leftu= s->dsp.add_hfyu_left_prediction(udst, s->temp[1], width2, leftu);
                        leftv= s->dsp.add_hfyu_left_prediction(vdst, s->temp[2], width2, leftv);
                    }
                    if (s->predictor == PLANE) {
                        if (cy > s->interlaced) {
                            s->dsp.add_bytes(ydst, ydst - fake_ystride, width);
                            if (!(s->flags & CODEC_FLAG_GRAY)) {
                                s->dsp.add_bytes(udst, udst - fake_ustride, width2);
                                s->dsp.add_bytes(vdst, vdst - fake_vstride, width2);
                            }
                        }
                    }
                }
                draw_slice(s, p, height);

                break;
            case MEDIAN:
                /* first line except first 2 pixels is left predicted */
                decode_422_bitstream(s, width - 2);
                lefty= s->dsp.add_hfyu_left_prediction(p->data[0] + 2, s->temp[0], width - 2, lefty);
                if (!(s->flags & CODEC_FLAG_GRAY)) {
                    leftu = s->dsp.add_hfyu_left_prediction(p->data[1] + 1, s->temp[1], width2 - 1, leftu);
                    leftv = s->dsp.add_hfyu_left_prediction(p->data[2] + 1, s->temp[2], width2 - 1, leftv);
                }

                cy = y = 1;

                /* second line is left predicted for interlaced case */
                if (s->interlaced) {
                    decode_422_bitstream(s, width);
                    lefty = s->dsp.add_hfyu_left_prediction(p->data[0] + p->linesize[0], s->temp[0], width, lefty);
                    if (!(s->flags & CODEC_FLAG_GRAY)) {
                        leftu = s->dsp.add_hfyu_left_prediction(p->data[1] + p->linesize[2], s->temp[1], width2, leftu);
                        leftv = s->dsp.add_hfyu_left_prediction(p->data[2] + p->linesize[1], s->temp[2], width2, leftv);
                    }
                    y++; cy++;
                }

                /* next 4 pixels are left predicted too */
                decode_422_bitstream(s, 4);
                lefty = s->dsp.add_hfyu_left_prediction(p->data[0] + fake_ystride, s->temp[0], 4, lefty);
                if (!(s->flags&CODEC_FLAG_GRAY)) {
                    leftu = s->dsp.add_hfyu_left_prediction(p->data[1] + fake_ustride, s->temp[1], 2, leftu);
                    leftv = s->dsp.add_hfyu_left_prediction(p->data[2] + fake_vstride, s->temp[2], 2, leftv);
                }

                /* next line except the first 4 pixels is median predicted */
                lefttopy = p->data[0][3];
                decode_422_bitstream(s, width - 4);
                s->dsp.add_hfyu_median_prediction(p->data[0] + fake_ystride+4, p->data[0]+4, s->temp[0], width-4, &lefty, &lefttopy);
                if (!(s->flags&CODEC_FLAG_GRAY)) {
                    lefttopu = p->data[1][1];
                    lefttopv = p->data[2][1];
                    s->dsp.add_hfyu_median_prediction(p->data[1] + fake_ustride+2, p->data[1] + 2, s->temp[1], width2 - 2, &leftu, &lefttopu);
                    s->dsp.add_hfyu_median_prediction(p->data[2] + fake_vstride+2, p->data[2] + 2, s->temp[2], width2 - 2, &leftv, &lefttopv);
                }
                y++; cy++;

                for (; y<height; y++, cy++) {
                    uint8_t *ydst, *udst, *vdst;

                    if (s->bitstream_bpp == 12) {
                        while (2 * cy > y) {
                            decode_gray_bitstream(s, width);
                            ydst = p->data[0] + p->linesize[0] * y;
                            s->dsp.add_hfyu_median_prediction(ydst, ydst - fake_ystride, s->temp[0], width, &lefty, &lefttopy);
                            y++;
                        }
                        if (y >= height) break;
                    }
                    draw_slice(s, p, y);

                    decode_422_bitstream(s, width);

                    ydst = p->data[0] + p->linesize[0] * y;
                    udst = p->data[1] + p->linesize[1] * cy;
                    vdst = p->data[2] + p->linesize[2] * cy;

                    s->dsp.add_hfyu_median_prediction(ydst, ydst - fake_ystride, s->temp[0], width, &lefty, &lefttopy);
                    if (!(s->flags & CODEC_FLAG_GRAY)) {
                        s->dsp.add_hfyu_median_prediction(udst, udst - fake_ustride, s->temp[1], width2, &leftu, &lefttopu);
                        s->dsp.add_hfyu_median_prediction(vdst, vdst - fake_vstride, s->temp[2], width2, &leftv, &lefttopv);
                    }
                }

                draw_slice(s, p, height);
                break;
            }
        }
    } else {
        int y;
        int leftr, leftg, leftb, lefta;
        const int last_line = (height - 1) * p->linesize[0];

        if (s->bitstream_bpp == 32) {
            lefta = p->data[0][last_line+A] = get_bits(&s->gb, 8);
            leftr = p->data[0][last_line+R] = get_bits(&s->gb, 8);
            leftg = p->data[0][last_line+G] = get_bits(&s->gb, 8);
            leftb = p->data[0][last_line+B] = get_bits(&s->gb, 8);
        } else {
            leftr = p->data[0][last_line+R] = get_bits(&s->gb, 8);
            leftg = p->data[0][last_line+G] = get_bits(&s->gb, 8);
            leftb = p->data[0][last_line+B] = get_bits(&s->gb, 8);
            lefta = p->data[0][last_line+A] = 255;
            skip_bits(&s->gb, 8);
        }

        if (s->bgr32) {
            switch (s->predictor) {
            case LEFT:
            case PLANE:
                decode_bgr_bitstream(s, width - 1);
                s->dsp.add_hfyu_left_prediction_bgr32(p->data[0] + last_line+4, s->temp[0], width - 1, &leftr, &leftg, &leftb, &lefta);

                for (y = s->height - 2; y >= 0; y--) { //Yes it is stored upside down.
                    decode_bgr_bitstream(s, width);

                    s->dsp.add_hfyu_left_prediction_bgr32(p->data[0] + p->linesize[0]*y, s->temp[0], width, &leftr, &leftg, &leftb, &lefta);
                    if (s->predictor == PLANE) {
                        if (s->bitstream_bpp != 32) lefta = 0;
                        if ((y & s->interlaced) == 0 &&
                            y < s->height - 1 - s->interlaced) {
                            s->dsp.add_bytes(p->data[0] + p->linesize[0] * y,
                                             p->data[0] + p->linesize[0] * y +
                                             fake_ystride, fake_ystride);
                        }
                    }
                }
                // just 1 large slice as this is not possible in reverse order
                draw_slice(s, p, height);
                break;
            default:
                av_log(avctx, AV_LOG_ERROR,
                       "prediction type not supported!\n");
            }
        }else{
            av_log(avctx, AV_LOG_ERROR,
                   "BGR24 output is not implemented yet\n");
            return AVERROR_PATCHWELCOME;
        }
    }
    emms_c();

    *got_frame = 1;

    return (get_bits_count(&s->gb) + 31) / 32 * 4 + table_size;
}

static av_cold int decode_end(AVCodecContext *avctx)
{
    HYuvContext *s = avctx->priv_data;
    int i;

    ff_huffyuv_common_end(s);
    av_freep(&s->bitstream_buffer);

    for (i = 0; i < 6; i++) {
        ff_free_vlc(&s->vlc[i]);
    }

    return 0;
}

#if CONFIG_HUFFYUV_DECODER
AVCodec ff_huffyuv_decoder = {
    .name             = "huffyuv",
    .type             = AVMEDIA_TYPE_VIDEO,
    .id               = AV_CODEC_ID_HUFFYUV,
    .priv_data_size   = sizeof(HYuvContext),
    .init             = decode_init,
    .close            = decode_end,
    .decode           = decode_frame,
    .capabilities     = CODEC_CAP_DR1 | CODEC_CAP_DRAW_HORIZ_BAND |
                        CODEC_CAP_FRAME_THREADS,
    .init_thread_copy = ONLY_IF_THREADS_ENABLED(decode_init_thread_copy),
    .long_name        = NULL_IF_CONFIG_SMALL("Huffyuv / HuffYUV"),
};
#endif

#if CONFIG_FFVHUFF_DECODER
AVCodec ff_ffvhuff_decoder = {
    .name             = "ffvhuff",
    .type             = AVMEDIA_TYPE_VIDEO,
    .id               = AV_CODEC_ID_FFVHUFF,
    .priv_data_size   = sizeof(HYuvContext),
    .init             = decode_init,
    .close            = decode_end,
    .decode           = decode_frame,
    .capabilities     = CODEC_CAP_DR1 | CODEC_CAP_DRAW_HORIZ_BAND |
                        CODEC_CAP_FRAME_THREADS,
    .init_thread_copy = ONLY_IF_THREADS_ENABLED(decode_init_thread_copy),
    .long_name        = NULL_IF_CONFIG_SMALL("Huffyuv FFmpeg variant"),
};
#endif
