2 * huffyuv codec for libavcodec
4 * Copyright (c) 2002-2003 Michael Niedermayer <michaelni@gmx.at>
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20 * see http://www.pcisys.net/~melanson/codecs/huffyuv.txt for a description of
26 * huffyuv codec for libavcodec.
35 typedef enum Predictor{
41 typedef struct HYuvContext{
42 AVCodecContext *avctx;
50 int yuy2; //use yuy2 instead of 422P
51 int bgr32; //use bgr32 instead of bgr24
56 uint8_t __align8 temp[3][2560];
57 uint64_t stats[3][256];
59 uint32_t bits[3][256];
62 uint8_t __align8 bitstream_buffer[1024*1024*3]; //FIXME dynamic alloc or some other solution
66 static const unsigned char classic_shift_luma[] = {
67 34,36,35,69,135,232,9,16,10,24,11,23,12,16,13,10,14,8,15,8,
68 16,8,17,20,16,10,207,206,205,236,11,8,10,21,9,23,8,8,199,70,
72 static const unsigned char classic_shift_chroma[] = {
73 66,36,37,38,39,40,41,75,76,77,110,239,144,81,82,83,84,85,118,183,
74 56,57,88,89,56,89,154,57,58,57,26,141,57,56,58,57,58,57,184,119,
75 214,245,116,83,82,49,80,79,78,77,44,75,41,40,39,38,37,36,34, 0
78 static const unsigned char classic_add_luma[256] = {
79 3, 9, 5, 12, 10, 35, 32, 29, 27, 50, 48, 45, 44, 41, 39, 37,
80 73, 70, 68, 65, 64, 61, 58, 56, 53, 50, 49, 46, 44, 41, 38, 36,
81 68, 65, 63, 61, 58, 55, 53, 51, 48, 46, 45, 43, 41, 39, 38, 36,
82 35, 33, 32, 30, 29, 27, 26, 25, 48, 47, 46, 44, 43, 41, 40, 39,
83 37, 36, 35, 34, 32, 31, 30, 28, 27, 26, 24, 23, 22, 20, 19, 37,
84 35, 34, 33, 31, 30, 29, 27, 26, 24, 23, 21, 20, 18, 17, 15, 29,
85 27, 26, 24, 22, 21, 19, 17, 16, 14, 26, 25, 23, 21, 19, 18, 16,
86 15, 27, 25, 23, 21, 19, 17, 16, 14, 26, 25, 23, 21, 18, 17, 14,
87 12, 17, 19, 13, 4, 9, 2, 11, 1, 7, 8, 0, 16, 3, 14, 6,
88 12, 10, 5, 15, 18, 11, 10, 13, 15, 16, 19, 20, 22, 24, 27, 15,
89 18, 20, 22, 24, 26, 14, 17, 20, 22, 24, 27, 15, 18, 20, 23, 25,
90 28, 16, 19, 22, 25, 28, 32, 36, 21, 25, 29, 33, 38, 42, 45, 49,
91 28, 31, 34, 37, 40, 42, 44, 47, 49, 50, 52, 54, 56, 57, 59, 60,
92 62, 64, 66, 67, 69, 35, 37, 39, 40, 42, 43, 45, 47, 48, 51, 52,
93 54, 55, 57, 59, 60, 62, 63, 66, 67, 69, 71, 72, 38, 40, 42, 43,
94 46, 47, 49, 51, 26, 28, 30, 31, 33, 34, 18, 19, 11, 13, 7, 8,
97 static const unsigned char classic_add_chroma[256] = {
98 3, 1, 2, 2, 2, 2, 3, 3, 7, 5, 7, 5, 8, 6, 11, 9,
99 7, 13, 11, 10, 9, 8, 7, 5, 9, 7, 6, 4, 7, 5, 8, 7,
100 11, 8, 13, 11, 19, 15, 22, 23, 20, 33, 32, 28, 27, 29, 51, 77,
101 43, 45, 76, 81, 46, 82, 75, 55, 56,144, 58, 80, 60, 74,147, 63,
102 143, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79,
103 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 27, 30, 21, 22,
104 17, 14, 5, 6,100, 54, 47, 50, 51, 53,106,107,108,109,110,111,
105 112,113,114,115, 4,117,118, 92, 94,121,122, 3,124,103, 2, 1,
106 0,129,130,131,120,119,126,125,136,137,138,139,140,141,142,134,
107 135,132,133,104, 64,101, 62, 57,102, 95, 93, 59, 61, 28, 97, 96,
108 52, 49, 48, 29, 32, 25, 24, 46, 23, 98, 45, 44, 43, 20, 42, 41,
109 19, 18, 99, 40, 15, 39, 38, 16, 13, 12, 11, 37, 10, 9, 8, 36,
110 7,128,127,105,123,116, 35, 34, 33,145, 31, 79, 42,146, 78, 26,
111 83, 48, 49, 50, 44, 47, 26, 31, 30, 18, 17, 19, 21, 24, 25, 13,
112 14, 16, 17, 18, 20, 21, 12, 14, 15, 9, 10, 6, 9, 6, 5, 8,
113 6, 12, 8, 10, 7, 9, 6, 4, 6, 2, 2, 3, 3, 3, 3, 2,
116 static inline int add_left_prediction(uint8_t *dst, uint8_t *src, int w, int acc){
119 for(i=0; i<w-1; i++){
135 static inline void add_median_prediction(uint8_t *dst, uint8_t *src1, uint8_t *diff, int w, int *left, int *left_top){
143 l= mid_pred(l, src1[i], (l + src1[i] - lt)&0xFF) + diff[i];
152 static inline void add_left_prediction_bgr32(uint8_t *dst, uint8_t *src, int w, int *red, int *green, int *blue){
174 static inline int sub_left_prediction(HYuvContext *s, uint8_t *dst, uint8_t *src, int w, int left){
178 const int temp= src[i];
185 const int temp= src[i];
189 s->dsp.diff_bytes(dst+16, src+16, src+15, w-16);
194 static void read_len_table(uint8_t *dst, GetBitContext *gb){
198 repeat= get_bits(gb, 3);
199 val = get_bits(gb, 5);
201 repeat= get_bits(gb, 8);
202 //printf("%d %d\n", val, repeat);
208 static int generate_bits_table(uint32_t *dst, uint8_t *len_table){
212 for(len=32; len>0; len--){
213 for(index=0; index<256; index++){
214 if(len_table[index]==len)
218 av_log(NULL, AV_LOG_ERROR, "Error generating huffman table\n");
226 static void generate_len_table(uint8_t *dst, uint64_t *stats, int size){
227 uint64_t counts[2*size];
231 for(offset=1; ; offset<<=1){
232 for(i=0; i<size; i++){
233 counts[i]= stats[i] + offset - 1;
236 for(next=size; next<size*2; next++){
240 min1=min2= INT64_MAX;
243 for(i=0; i<next; i++){
244 if(min2 > counts[i]){
245 if(min1 > counts[i]){
257 if(min2==INT64_MAX) break;
259 counts[next]= min1 + min2;
261 counts[min2_i]= INT64_MAX;
267 for(i=0; i<size; i++){
271 for(len=0; up[index] != -1; len++)
282 static int read_huffman_tables(HYuvContext *s, uint8_t *src, int length){
286 init_get_bits(&gb, src, length*8);
289 read_len_table(s->len[i], &gb);
291 if(generate_bits_table(s->bits[i], s->len[i])<0){
295 for(j=0; j<256; j++){
296 printf("%6X, %2d, %3d\n", s->bits[i][j], s->len[i][j], j);
299 init_vlc(&s->vlc[i], VLC_BITS, 256, s->len[i], 1, 1, s->bits[i], 4, 4);
305 static int read_old_huffman_tables(HYuvContext *s){
310 init_get_bits(&gb, classic_shift_luma, sizeof(classic_shift_luma)*8);
311 read_len_table(s->len[0], &gb);
312 init_get_bits(&gb, classic_shift_chroma, sizeof(classic_shift_chroma)*8);
313 read_len_table(s->len[1], &gb);
315 for(i=0; i<256; i++) s->bits[0][i] = classic_add_luma [i];
316 for(i=0; i<256; i++) s->bits[1][i] = classic_add_chroma[i];
318 if(s->bitstream_bpp >= 24){
319 memcpy(s->bits[1], s->bits[0], 256*sizeof(uint32_t));
320 memcpy(s->len[1] , s->len [0], 256*sizeof(uint8_t));
322 memcpy(s->bits[2], s->bits[1], 256*sizeof(uint32_t));
323 memcpy(s->len[2] , s->len [1], 256*sizeof(uint8_t));
326 init_vlc(&s->vlc[i], VLC_BITS, 256, s->len[i], 1, 1, s->bits[i], 4, 4);
330 fprintf(stderr, "v1 huffyuv is not supported \n");
335 static int decode_init(AVCodecContext *avctx)
337 HYuvContext *s = avctx->priv_data;
341 s->flags= avctx->flags;
343 dsputil_init(&s->dsp, avctx);
345 width= s->width= avctx->width;
346 height= s->height= avctx->height;
347 avctx->coded_frame= &s->picture;
350 assert(width && height);
351 //if(avctx->extradata)
352 // printf("extradata:%X, extradata_size:%d\n", *(uint32_t*)avctx->extradata, avctx->extradata_size);
353 if(avctx->extradata_size){
354 if((avctx->bits_per_sample&7) && avctx->bits_per_sample != 12)
355 s->version=1; // do such files exist at all?
364 method= ((uint8_t*)avctx->extradata)[0];
365 s->decorrelate= method&64 ? 1 : 0;
366 s->predictor= method&63;
367 s->bitstream_bpp= ((uint8_t*)avctx->extradata)[1];
368 if(s->bitstream_bpp==0)
369 s->bitstream_bpp= avctx->bits_per_sample&~7;
371 if(read_huffman_tables(s, ((uint8_t*)avctx->extradata)+4, avctx->extradata_size) < 0)
374 switch(avctx->bits_per_sample&7){
385 s->decorrelate= avctx->bits_per_sample >= 24;
388 s->predictor= MEDIAN;
392 s->predictor= LEFT; //OLD
396 s->bitstream_bpp= avctx->bits_per_sample & ~7;
398 if(read_old_huffman_tables(s) < 0)
402 s->interlaced= height > 288;
404 switch(s->bitstream_bpp){
406 avctx->pix_fmt = PIX_FMT_YUV420P;
410 avctx->pix_fmt = PIX_FMT_YUV422;
412 avctx->pix_fmt = PIX_FMT_YUV422P;
418 avctx->pix_fmt = PIX_FMT_RGBA32;
420 avctx->pix_fmt = PIX_FMT_BGR24;
427 // printf("pred:%d bpp:%d hbpp:%d il:%d\n", s->predictor, s->bitstream_bpp, avctx->bits_per_sample, s->interlaced);
432 static void store_table(HYuvContext *s, uint8_t *len){
434 int index= s->avctx->extradata_size;
440 for(; i<256 && len[i]==val && repeat<255; i++)
443 assert(val < 32 && val >0 && repeat<256 && repeat>0);
445 ((uint8_t*)s->avctx->extradata)[index++]= val;
446 ((uint8_t*)s->avctx->extradata)[index++]= repeat;
448 ((uint8_t*)s->avctx->extradata)[index++]= val | (repeat<<5);
452 s->avctx->extradata_size= index;
455 static int encode_init(AVCodecContext *avctx)
457 HYuvContext *s = avctx->priv_data;
458 int i, j, width, height;
461 s->flags= avctx->flags;
463 dsputil_init(&s->dsp, avctx);
465 width= s->width= avctx->width;
466 height= s->height= avctx->height;
468 assert(width && height);
470 avctx->extradata= av_mallocz(1024*30);
471 avctx->stats_out= av_mallocz(1024*30);
474 avctx->coded_frame= &s->picture;
476 switch(avctx->pix_fmt){
477 case PIX_FMT_YUV420P:
478 if(avctx->strict_std_compliance>=0){
479 av_log(avctx, AV_LOG_ERROR, "YV12-huffyuv is experimental, there WILL be no compatbility! (use (v)strict=-1)\n");
482 s->bitstream_bpp= 12;
484 case PIX_FMT_YUV422P:
485 s->bitstream_bpp= 16;
488 av_log(avctx, AV_LOG_ERROR, "format not supported\n");
491 avctx->bits_per_sample= s->bitstream_bpp;
492 s->decorrelate= s->bitstream_bpp >= 24;
493 s->predictor= avctx->prediction_method;
495 ((uint8_t*)avctx->extradata)[0]= s->predictor;
496 ((uint8_t*)avctx->extradata)[1]= s->bitstream_bpp;
497 ((uint8_t*)avctx->extradata)[2]=
498 ((uint8_t*)avctx->extradata)[3]= 0;
499 s->avctx->extradata_size= 4;
502 char *p= avctx->stats_in;
512 for(j=0; j<256; j++){
513 s->stats[i][j]+= strtol(p, &next, 0);
514 if(next==p) return -1;
518 if(p[0]==0 || p[1]==0 || p[2]==0) break;
522 for(j=0; j<256; j++){
523 int d= FFMIN(j, 256-j);
525 s->stats[i][j]= 100000000/(d+1);
530 generate_len_table(s->len[i], s->stats[i], 256);
532 if(generate_bits_table(s->bits[i], s->len[i])<0){
536 store_table(s, s->len[i]);
543 s->interlaced= height > 288;
545 // printf("pred:%d bpp:%d hbpp:%d il:%d\n", s->predictor, s->bitstream_bpp, avctx->bits_per_sample, s->interlaced);
552 static void decode_422_bitstream(HYuvContext *s, int count){
557 for(i=0; i<count; i++){
558 s->temp[0][2*i ]= get_vlc2(&s->gb, s->vlc[0].table, VLC_BITS, 3);
559 s->temp[1][ i ]= get_vlc2(&s->gb, s->vlc[1].table, VLC_BITS, 3);
560 s->temp[0][2*i+1]= get_vlc2(&s->gb, s->vlc[0].table, VLC_BITS, 3);
561 s->temp[2][ i ]= get_vlc2(&s->gb, s->vlc[2].table, VLC_BITS, 3);
565 static void decode_gray_bitstream(HYuvContext *s, int count){
570 for(i=0; i<count; i++){
571 s->temp[0][2*i ]= get_vlc2(&s->gb, s->vlc[0].table, VLC_BITS, 3);
572 s->temp[0][2*i+1]= get_vlc2(&s->gb, s->vlc[0].table, VLC_BITS, 3);
576 static void encode_422_bitstream(HYuvContext *s, int count){
580 if(s->flags&CODEC_FLAG_PASS1){
581 for(i=0; i<count; i++){
582 s->stats[0][ s->temp[0][2*i ] ]++;
583 s->stats[1][ s->temp[1][ i ] ]++;
584 s->stats[0][ s->temp[0][2*i+1] ]++;
585 s->stats[2][ s->temp[2][ i ] ]++;
588 for(i=0; i<count; i++){
589 put_bits(&s->pb, s->len[0][ s->temp[0][2*i ] ], s->bits[0][ s->temp[0][2*i ] ]);
590 put_bits(&s->pb, s->len[1][ s->temp[1][ i ] ], s->bits[1][ s->temp[1][ i ] ]);
591 put_bits(&s->pb, s->len[0][ s->temp[0][2*i+1] ], s->bits[0][ s->temp[0][2*i+1] ]);
592 put_bits(&s->pb, s->len[2][ s->temp[2][ i ] ], s->bits[2][ s->temp[2][ i ] ]);
597 static void encode_gray_bitstream(HYuvContext *s, int count){
601 if(s->flags&CODEC_FLAG_PASS1){
602 for(i=0; i<count; i++){
603 s->stats[0][ s->temp[0][2*i ] ]++;
604 s->stats[0][ s->temp[0][2*i+1] ]++;
607 for(i=0; i<count; i++){
608 put_bits(&s->pb, s->len[0][ s->temp[0][2*i ] ], s->bits[0][ s->temp[0][2*i ] ]);
609 put_bits(&s->pb, s->len[0][ s->temp[0][2*i+1] ], s->bits[0][ s->temp[0][2*i+1] ]);
614 static void decode_bgr_bitstream(HYuvContext *s, int count){
618 if(s->bitstream_bpp==24){
619 for(i=0; i<count; i++){
620 s->temp[0][4*i+1]= get_vlc2(&s->gb, s->vlc[1].table, VLC_BITS, 3);
621 s->temp[0][4*i ]= get_vlc2(&s->gb, s->vlc[0].table, VLC_BITS, 3) + s->temp[0][4*i+1];
622 s->temp[0][4*i+2]= get_vlc2(&s->gb, s->vlc[2].table, VLC_BITS, 3) + s->temp[0][4*i+1];
625 for(i=0; i<count; i++){
626 s->temp[0][4*i+1]= get_vlc2(&s->gb, s->vlc[1].table, VLC_BITS, 3);
627 s->temp[0][4*i ]= get_vlc2(&s->gb, s->vlc[0].table, VLC_BITS, 3) + s->temp[0][4*i+1];
628 s->temp[0][4*i+2]= get_vlc2(&s->gb, s->vlc[2].table, VLC_BITS, 3) + s->temp[0][4*i+1];
629 get_vlc2(&s->gb, s->vlc[2].table, VLC_BITS, 3); //?!
633 if(s->bitstream_bpp==24){
634 for(i=0; i<count; i++){
635 s->temp[0][4*i ]= get_vlc2(&s->gb, s->vlc[0].table, VLC_BITS, 3);
636 s->temp[0][4*i+1]= get_vlc2(&s->gb, s->vlc[1].table, VLC_BITS, 3);
637 s->temp[0][4*i+2]= get_vlc2(&s->gb, s->vlc[2].table, VLC_BITS, 3);
640 for(i=0; i<count; i++){
641 s->temp[0][4*i ]= get_vlc2(&s->gb, s->vlc[0].table, VLC_BITS, 3);
642 s->temp[0][4*i+1]= get_vlc2(&s->gb, s->vlc[1].table, VLC_BITS, 3);
643 s->temp[0][4*i+2]= get_vlc2(&s->gb, s->vlc[2].table, VLC_BITS, 3);
644 get_vlc2(&s->gb, s->vlc[2].table, VLC_BITS, 3); //?!
650 static void draw_slice(HYuvContext *s, int y){
654 if(s->avctx->draw_horiz_band==NULL)
657 h= y - s->last_slice_end;
660 if(s->bitstream_bpp==12){
666 offset[0] = s->picture.linesize[0]*y;
667 offset[1] = s->picture.linesize[1]*cy;
668 offset[2] = s->picture.linesize[2]*cy;
672 s->avctx->draw_horiz_band(s->avctx, &s->picture, offset, y, 3, h);
674 s->last_slice_end= y + h;
677 static int decode_frame(AVCodecContext *avctx, void *data, int *data_size, uint8_t *buf, int buf_size){
678 HYuvContext *s = avctx->priv_data;
679 const int width= s->width;
680 const int width2= s->width>>1;
681 const int height= s->height;
682 int fake_ystride, fake_ustride, fake_vstride;
683 AVFrame * const p= &s->picture;
685 AVFrame *picture = data;
689 /* no supplementary picture */
693 s->dsp.bswap_buf((uint32_t*)s->bitstream_buffer, (uint32_t*)buf, buf_size/4);
695 init_get_bits(&s->gb, s->bitstream_buffer, buf_size*8);
698 avctx->release_buffer(avctx, p);
701 if(avctx->get_buffer(avctx, p) < 0){
702 av_log(avctx, AV_LOG_ERROR, "get_buffer() failed\n");
706 fake_ystride= s->interlaced ? p->linesize[0]*2 : p->linesize[0];
707 fake_ustride= s->interlaced ? p->linesize[1]*2 : p->linesize[1];
708 fake_vstride= s->interlaced ? p->linesize[2]*2 : p->linesize[2];
710 s->last_slice_end= 0;
712 if(s->bitstream_bpp<24){
714 int lefty, leftu, leftv;
715 int lefttopy, lefttopu, lefttopv;
718 p->data[0][3]= get_bits(&s->gb, 8);
719 p->data[0][2]= get_bits(&s->gb, 8);
720 p->data[0][1]= get_bits(&s->gb, 8);
721 p->data[0][0]= get_bits(&s->gb, 8);
723 av_log(avctx, AV_LOG_ERROR, "YUY2 output isnt implemenetd yet\n");
727 leftv= p->data[2][0]= get_bits(&s->gb, 8);
728 lefty= p->data[0][1]= get_bits(&s->gb, 8);
729 leftu= p->data[1][0]= get_bits(&s->gb, 8);
730 p->data[0][0]= get_bits(&s->gb, 8);
732 switch(s->predictor){
735 decode_422_bitstream(s, width-2);
736 lefty= add_left_prediction(p->data[0] + 2, s->temp[0], width-2, lefty);
737 if(!(s->flags&CODEC_FLAG_GRAY)){
738 leftu= add_left_prediction(p->data[1] + 1, s->temp[1], width2-1, leftu);
739 leftv= add_left_prediction(p->data[2] + 1, s->temp[2], width2-1, leftv);
742 for(cy=y=1; y<s->height; y++,cy++){
743 uint8_t *ydst, *udst, *vdst;
745 if(s->bitstream_bpp==12){
746 decode_gray_bitstream(s, width);
748 ydst= p->data[0] + p->linesize[0]*y;
750 lefty= add_left_prediction(ydst, s->temp[0], width, lefty);
751 if(s->predictor == PLANE){
753 s->dsp.add_bytes(ydst, ydst - fake_ystride, width);
756 if(y>=s->height) break;
761 ydst= p->data[0] + p->linesize[0]*y;
762 udst= p->data[1] + p->linesize[1]*cy;
763 vdst= p->data[2] + p->linesize[2]*cy;
765 decode_422_bitstream(s, width);
766 lefty= add_left_prediction(ydst, s->temp[0], width, lefty);
767 if(!(s->flags&CODEC_FLAG_GRAY)){
768 leftu= add_left_prediction(udst, s->temp[1], width2, leftu);
769 leftv= add_left_prediction(vdst, s->temp[2], width2, leftv);
771 if(s->predictor == PLANE){
772 if(cy>s->interlaced){
773 s->dsp.add_bytes(ydst, ydst - fake_ystride, width);
774 if(!(s->flags&CODEC_FLAG_GRAY)){
775 s->dsp.add_bytes(udst, udst - fake_ustride, width2);
776 s->dsp.add_bytes(vdst, vdst - fake_vstride, width2);
781 draw_slice(s, height);
785 /* first line except first 2 pixels is left predicted */
786 decode_422_bitstream(s, width-2);
787 lefty= add_left_prediction(p->data[0] + 2, s->temp[0], width-2, lefty);
788 if(!(s->flags&CODEC_FLAG_GRAY)){
789 leftu= add_left_prediction(p->data[1] + 1, s->temp[1], width2-1, leftu);
790 leftv= add_left_prediction(p->data[2] + 1, s->temp[2], width2-1, leftv);
795 /* second line is left predicted for interlaced case */
797 decode_422_bitstream(s, width);
798 lefty= add_left_prediction(p->data[0] + p->linesize[0], s->temp[0], width, lefty);
799 if(!(s->flags&CODEC_FLAG_GRAY)){
800 leftu= add_left_prediction(p->data[1] + p->linesize[2], s->temp[1], width2, leftu);
801 leftv= add_left_prediction(p->data[2] + p->linesize[1], s->temp[2], width2, leftv);
806 /* next 4 pixels are left predicted too */
807 decode_422_bitstream(s, 4);
808 lefty= add_left_prediction(p->data[0] + fake_ystride, s->temp[0], 4, lefty);
809 if(!(s->flags&CODEC_FLAG_GRAY)){
810 leftu= add_left_prediction(p->data[1] + fake_ustride, s->temp[1], 2, leftu);
811 leftv= add_left_prediction(p->data[2] + fake_vstride, s->temp[2], 2, leftv);
814 /* next line except the first 4 pixels is median predicted */
815 lefttopy= p->data[0][3];
816 decode_422_bitstream(s, width-4);
817 add_median_prediction(p->data[0] + fake_ystride+4, p->data[0]+4, s->temp[0], width-4, &lefty, &lefttopy);
818 if(!(s->flags&CODEC_FLAG_GRAY)){
819 lefttopu= p->data[1][1];
820 lefttopv= p->data[2][1];
821 add_median_prediction(p->data[1] + fake_ustride+2, p->data[1]+2, s->temp[1], width2-2, &leftu, &lefttopu);
822 add_median_prediction(p->data[2] + fake_vstride+2, p->data[2]+2, s->temp[2], width2-2, &leftv, &lefttopv);
826 for(; y<height; y++,cy++){
827 uint8_t *ydst, *udst, *vdst;
829 if(s->bitstream_bpp==12){
831 decode_gray_bitstream(s, width);
832 ydst= p->data[0] + p->linesize[0]*y;
833 add_median_prediction(ydst, ydst - fake_ystride, s->temp[0], width, &lefty, &lefttopy);
840 decode_422_bitstream(s, width);
842 ydst= p->data[0] + p->linesize[0]*y;
843 udst= p->data[1] + p->linesize[1]*cy;
844 vdst= p->data[2] + p->linesize[2]*cy;
846 add_median_prediction(ydst, ydst - fake_ystride, s->temp[0], width, &lefty, &lefttopy);
847 if(!(s->flags&CODEC_FLAG_GRAY)){
848 add_median_prediction(udst, udst - fake_ustride, s->temp[1], width2, &leftu, &lefttopu);
849 add_median_prediction(vdst, vdst - fake_vstride, s->temp[2], width2, &leftv, &lefttopv);
853 draw_slice(s, height);
859 int leftr, leftg, leftb;
860 const int last_line= (height-1)*p->linesize[0];
862 if(s->bitstream_bpp==32){
863 p->data[0][last_line+3]= get_bits(&s->gb, 8);
864 leftr= p->data[0][last_line+2]= get_bits(&s->gb, 8);
865 leftg= p->data[0][last_line+1]= get_bits(&s->gb, 8);
866 leftb= p->data[0][last_line+0]= get_bits(&s->gb, 8);
868 leftr= p->data[0][last_line+2]= get_bits(&s->gb, 8);
869 leftg= p->data[0][last_line+1]= get_bits(&s->gb, 8);
870 leftb= p->data[0][last_line+0]= get_bits(&s->gb, 8);
871 skip_bits(&s->gb, 8);
875 switch(s->predictor){
878 decode_bgr_bitstream(s, width-1);
879 add_left_prediction_bgr32(p->data[0] + last_line+4, s->temp[0], width-1, &leftr, &leftg, &leftb);
881 for(y=s->height-2; y>=0; y--){ //yes its stored upside down
882 decode_bgr_bitstream(s, width);
884 add_left_prediction_bgr32(p->data[0] + p->linesize[0]*y, s->temp[0], width, &leftr, &leftg, &leftb);
885 if(s->predictor == PLANE){
886 if((y&s->interlaced)==0){
887 s->dsp.add_bytes(p->data[0] + p->linesize[0]*y,
888 p->data[0] + p->linesize[0]*y + fake_ystride, fake_ystride);
892 draw_slice(s, height); // just 1 large slice as this isnt possible in reverse order
895 av_log(avctx, AV_LOG_ERROR, "prediction type not supported!\n");
899 av_log(avctx, AV_LOG_ERROR, "BGR24 output isnt implemenetd yet\n");
906 *data_size = sizeof(AVFrame);
908 return (get_bits_count(&s->gb)+31)/32*4;
911 static int decode_end(AVCodecContext *avctx)
913 HYuvContext *s = avctx->priv_data;
917 free_vlc(&s->vlc[i]);
920 avcodec_default_free_buffers(avctx);
925 static int encode_frame(AVCodecContext *avctx, unsigned char *buf, int buf_size, void *data){
926 HYuvContext *s = avctx->priv_data;
927 AVFrame *pict = data;
928 const int width= s->width;
929 const int width2= s->width>>1;
930 const int height= s->height;
931 const int fake_ystride= s->interlaced ? pict->linesize[0]*2 : pict->linesize[0];
932 const int fake_ustride= s->interlaced ? pict->linesize[1]*2 : pict->linesize[1];
933 const int fake_vstride= s->interlaced ? pict->linesize[2]*2 : pict->linesize[2];
934 AVFrame * const p= &s->picture;
937 init_put_bits(&s->pb, buf, buf_size);
940 p->pict_type= FF_I_TYPE;
943 if(avctx->pix_fmt == PIX_FMT_YUV422P || avctx->pix_fmt == PIX_FMT_YUV420P){
944 int lefty, leftu, leftv, y, cy;
946 put_bits(&s->pb, 8, leftv= p->data[2][0]);
947 put_bits(&s->pb, 8, lefty= p->data[0][1]);
948 put_bits(&s->pb, 8, leftu= p->data[1][0]);
949 put_bits(&s->pb, 8, p->data[0][0]);
951 lefty= sub_left_prediction(s, s->temp[0], p->data[0]+2, width-2 , lefty);
952 leftu= sub_left_prediction(s, s->temp[1], p->data[1]+1, width2-1, leftu);
953 leftv= sub_left_prediction(s, s->temp[2], p->data[2]+1, width2-1, leftv);
955 encode_422_bitstream(s, width-2);
957 if(s->predictor==MEDIAN){
958 int lefttopy, lefttopu, lefttopv;
961 lefty= sub_left_prediction(s, s->temp[0], p->data[0]+p->linesize[0], width , lefty);
962 leftu= sub_left_prediction(s, s->temp[1], p->data[1]+p->linesize[1], width2, leftu);
963 leftv= sub_left_prediction(s, s->temp[2], p->data[2]+p->linesize[2], width2, leftv);
965 encode_422_bitstream(s, width);
969 lefty= sub_left_prediction(s, s->temp[0], p->data[0]+fake_ystride, 4, lefty);
970 leftu= sub_left_prediction(s, s->temp[1], p->data[1]+fake_ystride, 2, leftu);
971 leftv= sub_left_prediction(s, s->temp[2], p->data[2]+fake_ystride, 2, leftv);
973 encode_422_bitstream(s, 4);
975 lefttopy= p->data[0][3];
976 lefttopu= p->data[1][1];
977 lefttopv= p->data[2][1];
978 s->dsp.sub_hfyu_median_prediction(s->temp[0], p->data[0]+4, p->data[0] + fake_ystride+4, width-4 , &lefty, &lefttopy);
979 s->dsp.sub_hfyu_median_prediction(s->temp[1], p->data[1]+2, p->data[1] + fake_ustride+2, width2-2, &leftu, &lefttopu);
980 s->dsp.sub_hfyu_median_prediction(s->temp[2], p->data[2]+2, p->data[2] + fake_vstride+2, width2-2, &leftv, &lefttopv);
981 encode_422_bitstream(s, width-4);
984 for(; y<height; y++,cy++){
985 uint8_t *ydst, *udst, *vdst;
987 if(s->bitstream_bpp==12){
989 ydst= p->data[0] + p->linesize[0]*y;
990 s->dsp.sub_hfyu_median_prediction(s->temp[0], ydst - fake_ystride, ydst, width , &lefty, &lefttopy);
991 encode_gray_bitstream(s, width);
996 ydst= p->data[0] + p->linesize[0]*y;
997 udst= p->data[1] + p->linesize[1]*cy;
998 vdst= p->data[2] + p->linesize[2]*cy;
1000 s->dsp.sub_hfyu_median_prediction(s->temp[0], ydst - fake_ystride, ydst, width , &lefty, &lefttopy);
1001 s->dsp.sub_hfyu_median_prediction(s->temp[1], udst - fake_ustride, udst, width2, &leftu, &lefttopu);
1002 s->dsp.sub_hfyu_median_prediction(s->temp[2], vdst - fake_vstride, vdst, width2, &leftv, &lefttopv);
1004 encode_422_bitstream(s, width);
1007 for(cy=y=1; y<height; y++,cy++){
1008 uint8_t *ydst, *udst, *vdst;
1010 /* encode a luma only line & y++ */
1011 if(s->bitstream_bpp==12){
1012 ydst= p->data[0] + p->linesize[0]*y;
1014 if(s->predictor == PLANE && s->interlaced < y){
1015 s->dsp.diff_bytes(s->temp[1], ydst, ydst - fake_ystride, width);
1017 lefty= sub_left_prediction(s, s->temp[0], s->temp[1], width , lefty);
1019 lefty= sub_left_prediction(s, s->temp[0], ydst, width , lefty);
1021 encode_gray_bitstream(s, width);
1023 if(y>=height) break;
1026 ydst= p->data[0] + p->linesize[0]*y;
1027 udst= p->data[1] + p->linesize[1]*cy;
1028 vdst= p->data[2] + p->linesize[2]*cy;
1030 if(s->predictor == PLANE && s->interlaced < cy){
1031 s->dsp.diff_bytes(s->temp[1], ydst, ydst - fake_ystride, width);
1032 s->dsp.diff_bytes(s->temp[2], udst, udst - fake_ustride, width2);
1033 s->dsp.diff_bytes(s->temp[2] + 1250, vdst, vdst - fake_vstride, width2);
1035 lefty= sub_left_prediction(s, s->temp[0], s->temp[1], width , lefty);
1036 leftu= sub_left_prediction(s, s->temp[1], s->temp[2], width2, leftu);
1037 leftv= sub_left_prediction(s, s->temp[2], s->temp[2] + 1250, width2, leftv);
1039 lefty= sub_left_prediction(s, s->temp[0], ydst, width , lefty);
1040 leftu= sub_left_prediction(s, s->temp[1], udst, width2, leftu);
1041 leftv= sub_left_prediction(s, s->temp[2], vdst, width2, leftv);
1044 encode_422_bitstream(s, width);
1048 av_log(avctx, AV_LOG_ERROR, "Format not supported!\n");
1052 size= (get_bit_count(&s->pb)+31)/32;
1054 if((s->flags&CODEC_FLAG_PASS1) && (s->picture_number&31)==0){
1056 char *p= avctx->stats_out;
1058 for(j=0; j<256; j++){
1059 sprintf(p, "%llu ", s->stats[i][j]);
1067 flush_put_bits(&s->pb);
1068 s->dsp.bswap_buf((uint32_t*)buf, (uint32_t*)buf, size);
1071 s->picture_number++;
1076 static int encode_end(AVCodecContext *avctx)
1078 // HYuvContext *s = avctx->priv_data;
1080 av_freep(&avctx->extradata);
1081 av_freep(&avctx->stats_out);
1086 static const AVOption huffyuv_options[] =
1088 AVOPTION_CODEC_INT("prediction_method", "prediction_method", prediction_method, 0, 2, 0),
1092 AVCodec huffyuv_decoder = {
1096 sizeof(HYuvContext),
1101 CODEC_CAP_DR1 | CODEC_CAP_DRAW_HORIZ_BAND,
1105 #ifdef CONFIG_ENCODERS
1107 AVCodec huffyuv_encoder = {
1111 sizeof(HYuvContext),
1115 .options = huffyuv_options,
1118 #endif //CONFIG_ENCODERS