Mercurial > libavcodec.hg
annotate ffv1.c @ 2339:b7bb00973f99 libavcodec
switch ffv1 to the put/get_symbol() from snow
| author | michael |
|---|---|
| date | Sun, 31 Oct 2004 12:22:00 +0000 |
| parents | 37516ec97cd6 |
| children | 582e635cfa08 |
| rev | line source |
|---|---|
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1 /* |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
2 * FFV1 codec for libavcodec |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
3 * |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
4 * Copyright (c) 2003 Michael Niedermayer <michaelni@gmx.at> |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
5 * |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
6 * This library is free software; you can redistribute it and/or |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
7 * modify it under the terms of the GNU Lesser General Public |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
8 * License as published by the Free Software Foundation; either |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
9 * version 2 of the License, or (at your option) any later version. |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
10 * |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
11 * This library is distributed in the hope that it will be useful, |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
14 * Lesser General Public License for more details. |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
15 * |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
16 * You should have received a copy of the GNU Lesser General Public |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
17 * License along with this library; if not, write to the Free Software |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
19 * |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
20 */ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
21 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
22 /** |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
23 * @file ffv1.c |
|
1545
b340e83b8d0d
gcc->C99 and warning fixes patch by (Dan Christiansen <danchr at daimi dot au dot dk>)
michael
parents:
1522
diff
changeset
|
24 * FF Video Codec 1 (an experimental lossless codec) |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
25 */ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
26 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
27 #include "common.h" |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
28 #include "avcodec.h" |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
29 #include "dsputil.h" |
| 2338 | 30 #include "rangecoder.h" |
| 1306 | 31 #include "golomb.h" |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
32 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
33 #define MAX_PLANES 4 |
|
1302
c41f51b5d5d6
reducing memory consumption (reducing number of contexts and other stuff, no noticeable loss in compression rate)
michaelni
parents:
1300
diff
changeset
|
34 #define CONTEXT_SIZE 32 |
|
c41f51b5d5d6
reducing memory consumption (reducing number of contexts and other stuff, no noticeable loss in compression rate)
michaelni
parents:
1300
diff
changeset
|
35 |
| 1306 | 36 static const int8_t quant3[256]={ |
| 37 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, | |
| 38 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, | |
| 39 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, | |
| 40 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, | |
| 41 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, | |
| 42 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
43 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
44 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, |
| 1306 | 45 -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1, |
| 46 -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1, | |
| 47 -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1, | |
| 48 -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1, | |
| 49 -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1, | |
| 50 -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1, | |
| 51 -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1, | |
| 52 -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1, 0, | |
| 53 }; | |
| 54 static const int8_t quant5[256]={ | |
| 55 0, 1, 1, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
56 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, |
| 1306 | 57 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, |
| 58 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, | |
| 59 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, | |
| 60 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, | |
| 61 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, | |
| 62 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, | |
| 63 -2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2, | |
| 64 -2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2, | |
| 65 -2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2, | |
| 66 -2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2, | |
| 67 -2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2, | |
| 68 -2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2, | |
| 69 -2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2, | |
| 70 -2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-1,-1,-1, | |
| 71 }; | |
| 72 static const int8_t quant7[256]={ | |
| 73 0, 1, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, | |
| 74 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, | |
| 75 2, 2, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 3, | |
| 76 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, | |
| 77 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, | |
| 78 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, | |
| 79 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, | |
| 80 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, | |
| 81 -3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3, | |
| 82 -3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3, | |
| 83 -3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3, | |
| 84 -3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3, | |
| 85 -3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-3, | |
| 86 -3,-3,-3,-3,-3,-3,-3,-3,-3,-2,-2,-2,-2,-2,-2,-2, | |
| 87 -2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2, | |
| 88 -2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-1,-1, | |
| 89 }; | |
| 90 static const int8_t quant9[256]={ | |
| 91 0, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, | |
| 92 3, 3, 3, 3, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, | |
| 93 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, | |
| 94 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, | |
| 95 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, | |
| 96 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, | |
| 97 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, | |
| 98 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, | |
| 99 -4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4, | |
| 100 -4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4, | |
| 101 -4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4, | |
| 102 -4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4, | |
| 103 -4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4, | |
| 104 -4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4, | |
| 105 -4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-3,-3,-3,-3, | |
| 106 -3,-3,-3,-3,-3,-3,-3,-3,-3,-3,-2,-2,-2,-2,-1,-1, | |
| 107 }; | |
| 108 static const int8_t quant11[256]={ | |
| 109 0, 1, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 4, 4, 4, 4, | |
| 110 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, | |
| 111 4, 4, 4, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, | |
| 112 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, | |
| 113 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, | |
| 114 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, | |
| 115 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, | |
| 116 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, | |
| 117 -5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5, | |
| 118 -5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5, | |
| 119 -5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5, | |
| 120 -5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5, | |
| 121 -5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5, | |
| 122 -5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-4,-4, | |
| 123 -4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4,-4, | |
| 124 -4,-4,-4,-4,-4,-3,-3,-3,-3,-3,-3,-3,-2,-2,-2,-1, | |
| 125 }; | |
| 126 static const int8_t quant13[256]={ | |
| 127 0, 1, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4, 4, 4, 4, 4, | |
| 128 4, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, | |
| 129 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, | |
| 130 5, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, | |
| 131 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, | |
| 132 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, | |
| 133 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, | |
| 134 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, | |
| 135 -6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6, | |
| 136 -6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6, | |
| 137 -6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6, | |
| 138 -6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6, | |
| 139 -6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-6,-5, | |
| 140 -5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5, | |
| 141 -5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5,-5, | |
| 142 -4,-4,-4,-4,-4,-4,-4,-4,-4,-3,-3,-3,-3,-2,-2,-1, | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
143 }; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
144 |
| 1306 | 145 static const uint8_t log2_run[32]={ |
| 146 0, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, | |
| 147 4, 4, 5, 5, 6, 6, 7, 7, | |
| 148 8, 9,10,11,12,13,14,15, | |
| 149 }; | |
| 150 | |
| 151 typedef struct VlcState{ | |
| 152 int16_t drift; | |
| 153 uint16_t error_sum; | |
| 154 int8_t bias; | |
| 155 uint8_t count; | |
| 156 } VlcState; | |
| 157 | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
158 typedef struct PlaneContext{ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
159 int context_count; |
|
1302
c41f51b5d5d6
reducing memory consumption (reducing number of contexts and other stuff, no noticeable loss in compression rate)
michaelni
parents:
1300
diff
changeset
|
160 uint8_t (*state)[CONTEXT_SIZE]; |
| 1306 | 161 VlcState *vlc_state; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
162 uint8_t interlace_bit_state[2]; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
163 } PlaneContext; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
164 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
165 typedef struct FFV1Context{ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
166 AVCodecContext *avctx; |
| 2338 | 167 RangeCoder c; |
| 1306 | 168 GetBitContext gb; |
| 169 PutBitContext pb; | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
170 int version; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
171 int width, height; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
172 int chroma_h_shift, chroma_v_shift; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
173 int flags; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
174 int picture_number; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
175 AVFrame picture; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
176 int plane_count; |
| 1306 | 177 int ac; ///< 1-> CABAC 0-> golomb rice |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
178 PlaneContext plane[MAX_PLANES]; |
| 1306 | 179 int16_t quant_table[5][256]; |
| 1593 | 180 int run_index; |
| 181 int colorspace; | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
182 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
183 DSPContext dsp; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
184 }FFV1Context; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
185 |
| 1593 | 186 static always_inline int fold(int diff, int bits){ |
| 187 if(bits==8) | |
| 188 diff= (int8_t)diff; | |
| 189 else{ | |
| 190 diff+= 1<<(bits-1); | |
| 191 diff&=(1<<bits)-1; | |
| 192 diff-= 1<<(bits-1); | |
| 193 } | |
| 194 | |
| 195 return diff; | |
| 196 } | |
| 197 | |
| 198 static inline int predict(int_fast16_t *src, int_fast16_t *last){ | |
| 1306 | 199 const int LT= last[-1]; |
| 200 const int T= last[ 0]; | |
| 201 const int L = src[-1]; | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
202 |
| 1360 | 203 return mid_pred(L, L + T - LT, T); |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
204 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
205 |
| 1593 | 206 static inline int get_context(FFV1Context *f, int_fast16_t *src, int_fast16_t *last, int_fast16_t *last2){ |
| 1306 | 207 const int LT= last[-1]; |
| 208 const int T= last[ 0]; | |
| 209 const int RT= last[ 1]; | |
| 210 const int L = src[-1]; | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
211 |
| 1306 | 212 if(f->quant_table[3][127]){ |
| 213 const int TT= last2[0]; | |
| 214 const int LL= src[-2]; | |
| 215 return f->quant_table[0][(L-LT) & 0xFF] + f->quant_table[1][(LT-T) & 0xFF] + f->quant_table[2][(T-RT) & 0xFF] | |
| 216 +f->quant_table[3][(LL-L) & 0xFF] + f->quant_table[4][(TT-T) & 0xFF]; | |
| 217 }else | |
| 218 return f->quant_table[0][(L-LT) & 0xFF] + f->quant_table[1][(LT-T) & 0xFF] + f->quant_table[2][(T-RT) & 0xFF]; | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
219 } |
|
1302
c41f51b5d5d6
reducing memory consumption (reducing number of contexts and other stuff, no noticeable loss in compression rate)
michaelni
parents:
1300
diff
changeset
|
220 |
| 2339 | 221 static inline void put_symbol(RangeCoder *c, uint8_t *state, int v, int is_signed){ |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
222 int i; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
223 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
224 if(v){ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
225 const int a= ABS(v); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
226 const int e= av_log2(a); |
| 2338 | 227 put_rac(c, state+0, 0); |
|
1336
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
228 |
| 2339 | 229 assert(e<=9); |
| 230 | |
|
1336
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
231 for(i=0; i<e; i++){ |
| 2339 | 232 put_rac(c, state+1+i, 1); //1..10 |
| 233 } | |
| 234 put_rac(c, state+1+i, 0); | |
| 235 | |
| 236 for(i=e-1; i>=0; i--){ | |
| 237 put_rac(c, state+22+i, (a>>i)&1); //22..31 | |
|
1336
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
238 } |
|
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
239 |
| 2339 | 240 if(is_signed) |
| 241 put_rac(c, state+11 + e, v < 0); //11..21 | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
242 }else{ |
| 2338 | 243 put_rac(c, state+0, 1); |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
244 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
245 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
246 |
| 2339 | 247 static inline int get_symbol(RangeCoder *c, uint8_t *state, int is_signed){ |
| 2338 | 248 if(get_rac(c, state+0)) |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
249 return 0; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
250 else{ |
| 2339 | 251 int i, e, a; |
| 252 e= 0; | |
| 253 while(get_rac(c, state+1 + e)){ //1..10 | |
| 254 e++; | |
| 255 } | |
| 256 assert(e<=9); | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
257 |
| 2339 | 258 a= 1; |
| 259 for(i=e-1; i>=0; i--){ | |
| 260 a += a + get_rac(c, state+22 + i); //22..31 | |
| 261 } | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
262 |
| 2339 | 263 if(is_signed && get_rac(c, state+11 + e)) //11..21 |
| 264 return -a; | |
| 265 else | |
| 266 return a; | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
267 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
268 } |
| 1306 | 269 |
| 270 static inline void update_vlc_state(VlcState * const state, const int v){ | |
| 271 int drift= state->drift; | |
| 272 int count= state->count; | |
| 273 state->error_sum += ABS(v); | |
| 274 drift += v; | |
| 275 | |
| 276 if(count == 128){ //FIXME variable | |
| 277 count >>= 1; | |
| 278 drift >>= 1; | |
| 279 state->error_sum >>= 1; | |
| 280 } | |
| 281 count++; | |
| 282 | |
| 283 if(drift <= -count){ | |
| 284 if(state->bias > -128) state->bias--; | |
| 285 | |
| 286 drift += count; | |
| 287 if(drift <= -count) | |
| 288 drift= -count + 1; | |
| 289 }else if(drift > 0){ | |
| 290 if(state->bias < 127) state->bias++; | |
| 291 | |
| 292 drift -= count; | |
| 293 if(drift > 0) | |
| 294 drift= 0; | |
| 295 } | |
| 296 | |
| 297 state->drift= drift; | |
| 298 state->count= count; | |
| 299 } | |
| 300 | |
| 1593 | 301 static inline void put_vlc_symbol(PutBitContext *pb, VlcState * const state, int v, int bits){ |
| 1306 | 302 int i, k, code; |
| 303 //printf("final: %d ", v); | |
| 1593 | 304 v = fold(v - state->bias, bits); |
| 305 | |
| 1306 | 306 i= state->count; |
| 307 k=0; | |
| 308 while(i < state->error_sum){ //FIXME optimize | |
| 309 k++; | |
| 310 i += i; | |
| 311 } | |
|
1361
8479b875a989
golomb rice code cleanup / simplify (~0.5% compression gain and slightly faster)
michaelni
parents:
1360
diff
changeset
|
312 |
|
8479b875a989
golomb rice code cleanup / simplify (~0.5% compression gain and slightly faster)
michaelni
parents:
1360
diff
changeset
|
313 assert(k<=8); |
|
8479b875a989
golomb rice code cleanup / simplify (~0.5% compression gain and slightly faster)
michaelni
parents:
1360
diff
changeset
|
314 |
| 1306 | 315 #if 0 // JPEG LS |
| 316 if(k==0 && 2*state->drift <= - state->count) code= v ^ (-1); | |
| 317 else code= v; | |
| 318 #else | |
| 319 code= v ^ ((2*state->drift + state->count)>>31); | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
320 #endif |
| 1306 | 321 |
| 322 //printf("v:%d/%d bias:%d error:%d drift:%d count:%d k:%d\n", v, code, state->bias, state->error_sum, state->drift, state->count, k); | |
| 2220 | 323 set_sr_golomb(pb, code, k, 12, bits); |
| 1306 | 324 |
| 325 update_vlc_state(state, v); | |
| 326 } | |
| 327 | |
| 1593 | 328 static inline int get_vlc_symbol(GetBitContext *gb, VlcState * const state, int bits){ |
| 1306 | 329 int k, i, v, ret; |
| 330 | |
| 331 i= state->count; | |
| 332 k=0; | |
| 333 while(i < state->error_sum){ //FIXME optimize | |
| 334 k++; | |
| 335 i += i; | |
| 336 } | |
|
1361
8479b875a989
golomb rice code cleanup / simplify (~0.5% compression gain and slightly faster)
michaelni
parents:
1360
diff
changeset
|
337 |
|
8479b875a989
golomb rice code cleanup / simplify (~0.5% compression gain and slightly faster)
michaelni
parents:
1360
diff
changeset
|
338 assert(k<=8); |
|
8479b875a989
golomb rice code cleanup / simplify (~0.5% compression gain and slightly faster)
michaelni
parents:
1360
diff
changeset
|
339 |
| 2220 | 340 v= get_sr_golomb(gb, k, 12, bits); |
| 1306 | 341 //printf("v:%d bias:%d error:%d drift:%d count:%d k:%d", v, state->bias, state->error_sum, state->drift, state->count, k); |
|
1361
8479b875a989
golomb rice code cleanup / simplify (~0.5% compression gain and slightly faster)
michaelni
parents:
1360
diff
changeset
|
342 |
| 1306 | 343 #if 0 // JPEG LS |
| 344 if(k==0 && 2*state->drift <= - state->count) v ^= (-1); | |
| 345 #else | |
| 346 v ^= ((2*state->drift + state->count)>>31); | |
| 347 #endif | |
| 348 | |
| 1593 | 349 ret= fold(v + state->bias, bits); |
| 1306 | 350 |
| 351 update_vlc_state(state, v); | |
| 352 //printf("final: %d\n", ret); | |
| 353 return ret; | |
| 354 } | |
| 355 | |
| 1605 | 356 static inline void encode_line(FFV1Context *s, int w, int_fast16_t *sample[2], int plane_index, int bits){ |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
357 PlaneContext * const p= &s->plane[plane_index]; |
| 2338 | 358 RangeCoder * const c= &s->c; |
| 1593 | 359 int x; |
| 360 int run_index= s->run_index; | |
| 361 int run_count=0; | |
| 362 int run_mode=0; | |
| 363 | |
| 364 for(x=0; x<w; x++){ | |
| 365 int diff, context; | |
| 366 | |
| 1999 | 367 context= get_context(s, sample[0]+x, sample[1]+x, sample[2]+x); |
| 368 diff= sample[0][x] - predict(sample[0]+x, sample[1]+x); | |
| 1593 | 369 |
| 370 if(context < 0){ | |
| 371 context = -context; | |
| 372 diff= -diff; | |
| 373 } | |
| 374 | |
| 375 diff= fold(diff, bits); | |
| 376 | |
| 377 if(s->ac){ | |
| 2339 | 378 put_symbol(c, p->state[context], diff, 1); |
| 1593 | 379 }else{ |
| 380 if(context == 0) run_mode=1; | |
| 381 | |
| 382 if(run_mode){ | |
| 383 | |
| 384 if(diff){ | |
| 385 while(run_count >= 1<<log2_run[run_index]){ | |
| 386 run_count -= 1<<log2_run[run_index]; | |
| 387 run_index++; | |
| 388 put_bits(&s->pb, 1, 1); | |
| 389 } | |
| 390 | |
| 391 put_bits(&s->pb, 1 + log2_run[run_index], run_count); | |
| 392 if(run_index) run_index--; | |
| 393 run_count=0; | |
| 394 run_mode=0; | |
| 395 if(diff>0) diff--; | |
| 396 }else{ | |
| 397 run_count++; | |
| 398 } | |
| 399 } | |
| 400 | |
| 1786 | 401 // printf("count:%d index:%d, mode:%d, x:%d y:%d pos:%d\n", run_count, run_index, run_mode, x, y, (int)put_bits_count(&s->pb)); |
| 1593 | 402 |
| 403 if(run_mode == 0) | |
| 404 put_vlc_symbol(&s->pb, &p->vlc_state[context], diff, bits); | |
| 405 } | |
| 406 } | |
| 407 if(run_mode){ | |
| 408 while(run_count >= 1<<log2_run[run_index]){ | |
| 409 run_count -= 1<<log2_run[run_index]; | |
| 410 run_index++; | |
| 411 put_bits(&s->pb, 1, 1); | |
| 412 } | |
| 413 | |
| 414 if(run_count) | |
| 415 put_bits(&s->pb, 1, 1); | |
| 416 } | |
| 417 s->run_index= run_index; | |
| 418 } | |
| 419 | |
| 420 static void encode_plane(FFV1Context *s, uint8_t *src, int w, int h, int stride, int plane_index){ | |
| 1999 | 421 int x,y,i; |
| 2162 | 422 const int ring_size= s->avctx->context_model ? 3 : 2; |
| 1999 | 423 int_fast16_t sample_buffer[ring_size][w+6], *sample[ring_size]; |
| 1593 | 424 s->run_index=0; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
425 |
| 1337 | 426 memset(sample_buffer, 0, sizeof(sample_buffer)); |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
427 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
428 for(y=0; y<h; y++){ |
| 1999 | 429 for(i=0; i<ring_size; i++) |
| 430 sample[i]= sample_buffer[(h+i-y)%ring_size]+3; | |
| 1306 | 431 |
| 1999 | 432 sample[0][-1]= sample[1][0 ]; |
| 433 sample[1][ w]= sample[1][w-1]; | |
| 1593 | 434 //{START_TIMER |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
435 for(x=0; x<w; x++){ |
| 1999 | 436 sample[0][x]= src[x + stride*y]; |
| 1593 | 437 } |
| 438 encode_line(s, w, sample, plane_index, 8); | |
| 439 //STOP_TIMER("encode line")} | |
| 440 } | |
| 441 } | |
|
1302
c41f51b5d5d6
reducing memory consumption (reducing number of contexts and other stuff, no noticeable loss in compression rate)
michaelni
parents:
1300
diff
changeset
|
442 |
| 1593 | 443 static void encode_rgb_frame(FFV1Context *s, uint32_t *src, int w, int h, int stride){ |
| 1999 | 444 int x, y, p, i; |
| 2162 | 445 const int ring_size= s->avctx->context_model ? 3 : 2; |
| 1999 | 446 int_fast16_t sample_buffer[3][ring_size][w+6], *sample[3][ring_size]; |
| 1593 | 447 s->run_index=0; |
| 448 | |
| 449 memset(sample_buffer, 0, sizeof(sample_buffer)); | |
| 450 | |
| 451 for(y=0; y<h; y++){ | |
| 1999 | 452 for(i=0; i<ring_size; i++) |
| 453 for(p=0; p<3; p++) | |
| 454 sample[p][i]= sample_buffer[p][(h+i-y)%ring_size]+3; | |
| 455 | |
| 1593 | 456 for(x=0; x<w; x++){ |
| 457 int v= src[x + stride*y]; | |
| 458 int b= v&0xFF; | |
| 459 int g= (v>>8)&0xFF; | |
| 460 int r= (v>>16)&0xFF; | |
| 461 | |
| 462 b -= g; | |
| 463 r -= g; | |
| 464 g += (b + r)>>2; | |
| 465 b += 0x100; | |
| 466 r += 0x100; | |
| 467 | |
| 468 // assert(g>=0 && b>=0 && r>=0); | |
| 469 // assert(g<256 && b<512 && r<512); | |
| 470 sample[0][0][x]= g; | |
| 471 sample[1][0][x]= b; | |
| 472 sample[2][0][x]= r; | |
| 473 } | |
| 474 for(p=0; p<3; p++){ | |
| 1999 | 475 sample[p][0][-1]= sample[p][1][0 ]; |
| 476 sample[p][1][ w]= sample[p][1][w-1]; | |
| 1593 | 477 encode_line(s, w, sample[p], FFMIN(p, 1), 9); |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
478 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
479 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
480 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
481 |
| 2338 | 482 static void write_quant_table(RangeCoder *c, int16_t *quant_table){ |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
483 int last=0; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
484 int i; |
| 2338 | 485 uint8_t state[CONTEXT_SIZE]; |
| 486 memset(state, 128, sizeof(state)); | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
487 |
| 1306 | 488 for(i=1; i<128 ; i++){ |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
489 if(quant_table[i] != quant_table[i-1]){ |
| 2339 | 490 put_symbol(c, state, i-last-1, 0); |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
491 last= i; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
492 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
493 } |
| 2339 | 494 put_symbol(c, state, i-last-1, 0); |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
495 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
496 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
497 static void write_header(FFV1Context *f){ |
| 2338 | 498 uint8_t state[CONTEXT_SIZE]; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
499 int i; |
| 2338 | 500 RangeCoder * const c= &f->c; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
501 |
| 2338 | 502 memset(state, 128, sizeof(state)); |
| 503 | |
| 2339 | 504 put_symbol(c, state, f->version, 0); |
| 505 put_symbol(c, state, f->avctx->coder_type, 0); | |
| 506 put_symbol(c, state, f->colorspace, 0); //YUV cs type | |
| 2338 | 507 put_rac(c, state, 1); //chroma planes |
| 2339 | 508 put_symbol(c, state, f->chroma_h_shift, 0); |
| 509 put_symbol(c, state, f->chroma_v_shift, 0); | |
| 2338 | 510 put_rac(c, state, 0); //no transparency plane |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
511 |
| 1306 | 512 for(i=0; i<5; i++) |
| 513 write_quant_table(c, f->quant_table[i]); | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
514 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
515 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
516 static int common_init(AVCodecContext *avctx){ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
517 FFV1Context *s = avctx->priv_data; |
|
1302
c41f51b5d5d6
reducing memory consumption (reducing number of contexts and other stuff, no noticeable loss in compression rate)
michaelni
parents:
1300
diff
changeset
|
518 int width, height; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
519 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
520 s->avctx= avctx; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
521 s->flags= avctx->flags; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
522 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
523 dsputil_init(&s->dsp, avctx); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
524 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
525 width= s->width= avctx->width; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
526 height= s->height= avctx->height; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
527 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
528 assert(width && height); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
529 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
530 return 0; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
531 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
532 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
533 static int encode_init(AVCodecContext *avctx) |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
534 { |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
535 FFV1Context *s = avctx->priv_data; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
536 int i; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
537 |
| 2218 | 538 if(avctx->strict_std_compliance >= 0){ |
| 539 av_log(avctx, AV_LOG_ERROR, "this codec is under development, files encoded with it wont be decodeable with future versions!!!\n" | |
| 540 "use vstrict=-1 to use it anyway\n"); | |
| 541 return -1; | |
| 542 } | |
| 543 | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
544 common_init(avctx); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
545 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
546 s->version=0; |
| 1306 | 547 s->ac= avctx->coder_type; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
548 |
|
1345
daf951f32697
merge U and V statistics, 33% reduction in memory requirement, compression rate better for some files worse for others, worst compression rate loss 0.05%
michaelni
parents:
1337
diff
changeset
|
549 s->plane_count=2; |
| 1306 | 550 for(i=0; i<256; i++){ |
| 551 s->quant_table[0][i]= quant11[i]; | |
| 552 s->quant_table[1][i]= 11*quant11[i]; | |
| 553 if(avctx->context_model==0){ | |
| 554 s->quant_table[2][i]= 11*11*quant11[i]; | |
| 555 s->quant_table[3][i]= | |
| 556 s->quant_table[4][i]=0; | |
| 557 }else{ | |
| 558 s->quant_table[2][i]= 11*11*quant5 [i]; | |
| 559 s->quant_table[3][i]= 5*11*11*quant5 [i]; | |
| 560 s->quant_table[4][i]= 5*5*11*11*quant5 [i]; | |
| 561 } | |
| 562 } | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
563 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
564 for(i=0; i<s->plane_count; i++){ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
565 PlaneContext * const p= &s->plane[i]; |
| 1306 | 566 |
| 567 if(avctx->context_model==0){ | |
| 568 p->context_count= (11*11*11+1)/2; | |
| 569 }else{ | |
| 570 p->context_count= (11*11*5*5*5+1)/2; | |
| 571 } | |
| 572 | |
| 573 if(s->ac){ | |
| 574 if(!p->state) p->state= av_malloc(CONTEXT_SIZE*p->context_count*sizeof(uint8_t)); | |
| 575 }else{ | |
| 576 if(!p->vlc_state) p->vlc_state= av_malloc(p->context_count*sizeof(VlcState)); | |
| 577 } | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
578 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
579 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
580 avctx->coded_frame= &s->picture; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
581 switch(avctx->pix_fmt){ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
582 case PIX_FMT_YUV444P: |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
583 case PIX_FMT_YUV422P: |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
584 case PIX_FMT_YUV420P: |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
585 case PIX_FMT_YUV411P: |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
586 case PIX_FMT_YUV410P: |
| 1593 | 587 s->colorspace= 0; |
| 588 break; | |
| 589 case PIX_FMT_RGBA32: | |
| 590 s->colorspace= 1; | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
591 break; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
592 default: |
|
1598
932d306bf1dc
av_log() patch by (Michel Bardiaux <mbardiaux at peaktime dot be>)
michael
parents:
1593
diff
changeset
|
593 av_log(avctx, AV_LOG_ERROR, "format not supported\n"); |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
594 return -1; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
595 } |
| 1593 | 596 avcodec_get_chroma_sub_sample(avctx->pix_fmt, &s->chroma_h_shift, &s->chroma_v_shift); |
| 597 | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
598 s->picture_number=0; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
599 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
600 return 0; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
601 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
602 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
603 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
604 static void clear_state(FFV1Context *f){ |
|
1302
c41f51b5d5d6
reducing memory consumption (reducing number of contexts and other stuff, no noticeable loss in compression rate)
michaelni
parents:
1300
diff
changeset
|
605 int i, j; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
606 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
607 for(i=0; i<f->plane_count; i++){ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
608 PlaneContext *p= &f->plane[i]; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
609 |
| 2338 | 610 p->interlace_bit_state[0]= 128; |
| 611 p->interlace_bit_state[1]= 128; | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
612 |
|
1302
c41f51b5d5d6
reducing memory consumption (reducing number of contexts and other stuff, no noticeable loss in compression rate)
michaelni
parents:
1300
diff
changeset
|
613 for(j=0; j<p->context_count; j++){ |
| 1306 | 614 if(f->ac){ |
| 2338 | 615 memset(p->state[j], 128, sizeof(uint8_t)*CONTEXT_SIZE); |
| 1306 | 616 }else{ |
| 617 p->vlc_state[j].drift= 0; | |
| 618 p->vlc_state[j].error_sum= 4; //FFMAX((RANGE + 32)/64, 2); | |
| 619 p->vlc_state[j].bias= 0; | |
| 620 p->vlc_state[j].count= 1; | |
| 621 } | |
|
1302
c41f51b5d5d6
reducing memory consumption (reducing number of contexts and other stuff, no noticeable loss in compression rate)
michaelni
parents:
1300
diff
changeset
|
622 } |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
623 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
624 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
625 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
626 static int encode_frame(AVCodecContext *avctx, unsigned char *buf, int buf_size, void *data){ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
627 FFV1Context *f = avctx->priv_data; |
| 2338 | 628 RangeCoder * const c= &f->c; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
629 AVFrame *pict = data; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
630 const int width= f->width; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
631 const int height= f->height; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
632 AVFrame * const p= &f->picture; |
| 1306 | 633 int used_count= 0; |
| 2338 | 634 uint8_t keystate=128; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
635 |
| 2338 | 636 ff_init_range_encoder(c, buf, buf_size); |
| 637 // ff_init_cabac_states(c, ff_h264_lps_range, ff_h264_mps_state, ff_h264_lps_state, 64); | |
| 638 ff_build_rac_states(c, 0.05*(1LL<<32), 256-8); | |
| 639 | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
640 *p = *pict; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
641 p->pict_type= FF_I_TYPE; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
642 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
643 if(avctx->gop_size==0 || f->picture_number % avctx->gop_size == 0){ |
| 2338 | 644 put_rac(c, &keystate, 1); |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
645 p->key_frame= 1; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
646 write_header(f); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
647 clear_state(f); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
648 }else{ |
| 2338 | 649 put_rac(c, &keystate, 0); |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
650 p->key_frame= 0; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
651 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
652 |
| 1306 | 653 if(!f->ac){ |
| 2338 | 654 used_count += ff_rac_terminate(c); |
| 1306 | 655 //printf("pos=%d\n", used_count); |
|
1522
79dddc5cd990
removed the obsolete and unused parameters of init_put_bits
alex
parents:
1453
diff
changeset
|
656 init_put_bits(&f->pb, buf + used_count, buf_size - used_count); |
| 1306 | 657 } |
| 658 | |
| 1593 | 659 if(f->colorspace==0){ |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
660 const int chroma_width = -((-width )>>f->chroma_h_shift); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
661 const int chroma_height= -((-height)>>f->chroma_v_shift); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
662 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
663 encode_plane(f, p->data[0], width, height, p->linesize[0], 0); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
664 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
665 encode_plane(f, p->data[1], chroma_width, chroma_height, p->linesize[1], 1); |
|
1345
daf951f32697
merge U and V statistics, 33% reduction in memory requirement, compression rate better for some files worse for others, worst compression rate loss 0.05%
michaelni
parents:
1337
diff
changeset
|
666 encode_plane(f, p->data[2], chroma_width, chroma_height, p->linesize[2], 1); |
| 1593 | 667 }else{ |
| 668 encode_rgb_frame(f, (uint32_t*)(p->data[0]), width, height, p->linesize[0]/4); | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
669 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
670 emms_c(); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
671 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
672 f->picture_number++; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
673 |
| 1306 | 674 if(f->ac){ |
| 2338 | 675 return ff_rac_terminate(c); |
| 1306 | 676 }else{ |
| 677 flush_put_bits(&f->pb); //nicer padding FIXME | |
| 1786 | 678 return used_count + (put_bits_count(&f->pb)+7)/8; |
| 1306 | 679 } |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
680 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
681 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
682 static void common_end(FFV1Context *s){ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
683 int i; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
684 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
685 for(i=0; i<s->plane_count; i++){ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
686 PlaneContext *p= &s->plane[i]; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
687 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
688 av_freep(&p->state); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
689 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
690 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
691 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
692 static int encode_end(AVCodecContext *avctx) |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
693 { |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
694 FFV1Context *s = avctx->priv_data; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
695 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
696 common_end(s); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
697 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
698 return 0; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
699 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
700 |
| 1605 | 701 static inline void decode_line(FFV1Context *s, int w, int_fast16_t *sample[2], int plane_index, int bits){ |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
702 PlaneContext * const p= &s->plane[plane_index]; |
| 2338 | 703 RangeCoder * const c= &s->c; |
| 1593 | 704 int x; |
| 705 int run_count=0; | |
| 706 int run_mode=0; | |
| 707 int run_index= s->run_index; | |
| 708 | |
| 709 for(x=0; x<w; x++){ | |
| 710 int diff, context, sign; | |
| 711 | |
| 712 context= get_context(s, sample[1] + x, sample[0] + x, sample[1] + x); | |
| 713 if(context < 0){ | |
| 714 context= -context; | |
| 715 sign=1; | |
| 716 }else | |
| 717 sign=0; | |
| 718 | |
| 719 | |
| 2339 | 720 if(s->ac){ |
| 721 diff= get_symbol(c, p->state[context], 1); | |
| 722 }else{ | |
| 1593 | 723 if(context == 0 && run_mode==0) run_mode=1; |
| 724 | |
| 725 if(run_mode){ | |
| 726 if(run_count==0 && run_mode==1){ | |
| 727 if(get_bits1(&s->gb)){ | |
| 728 run_count = 1<<log2_run[run_index]; | |
| 729 if(x + run_count <= w) run_index++; | |
| 730 }else{ | |
| 731 if(log2_run[run_index]) run_count = get_bits(&s->gb, log2_run[run_index]); | |
| 732 else run_count=0; | |
| 733 if(run_index) run_index--; | |
| 734 run_mode=2; | |
| 735 } | |
| 736 } | |
| 737 run_count--; | |
| 738 if(run_count < 0){ | |
| 739 run_mode=0; | |
| 740 run_count=0; | |
| 741 diff= get_vlc_symbol(&s->gb, &p->vlc_state[context], bits); | |
| 742 if(diff>=0) diff++; | |
| 743 }else | |
| 744 diff=0; | |
| 745 }else | |
| 746 diff= get_vlc_symbol(&s->gb, &p->vlc_state[context], bits); | |
| 747 | |
| 748 // printf("count:%d index:%d, mode:%d, x:%d y:%d pos:%d\n", run_count, run_index, run_mode, x, y, get_bits_count(&s->gb)); | |
| 749 } | |
| 750 | |
| 751 if(sign) diff= -diff; | |
| 752 | |
| 753 sample[1][x]= (predict(sample[1] + x, sample[0] + x) + diff) & ((1<<bits)-1); | |
| 754 } | |
| 755 s->run_index= run_index; | |
| 756 } | |
| 757 | |
| 758 static void decode_plane(FFV1Context *s, uint8_t *src, int w, int h, int stride, int plane_index){ | |
| 759 int x, y; | |
| 760 int_fast16_t sample_buffer[2][w+6]; | |
| 761 int_fast16_t *sample[2]= {sample_buffer[0]+3, sample_buffer[1]+3}; | |
| 762 | |
| 763 s->run_index=0; | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
764 |
| 1337 | 765 memset(sample_buffer, 0, sizeof(sample_buffer)); |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
766 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
767 for(y=0; y<h; y++){ |
| 1593 | 768 int_fast16_t *temp= sample[0]; //FIXME try a normal buffer |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
769 |
| 1337 | 770 sample[0]= sample[1]; |
| 771 sample[1]= temp; | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
772 |
| 1337 | 773 sample[1][-1]= sample[0][0 ]; |
| 774 sample[0][ w]= sample[0][w-1]; | |
| 1593 | 775 |
| 776 //{START_TIMER | |
| 777 decode_line(s, w, sample, plane_index, 8); | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
778 for(x=0; x<w; x++){ |
| 1593 | 779 src[x + stride*y]= sample[1][x]; |
| 780 } | |
| 781 //STOP_TIMER("decode-line")} | |
| 782 } | |
| 783 } | |
| 784 | |
| 785 static void decode_rgb_frame(FFV1Context *s, uint32_t *src, int w, int h, int stride){ | |
| 786 int x, y, p; | |
| 787 int_fast16_t sample_buffer[3][2][w+6]; | |
| 788 int_fast16_t *sample[3][2]= { | |
| 789 {sample_buffer[0][0]+3, sample_buffer[0][1]+3}, | |
| 790 {sample_buffer[1][0]+3, sample_buffer[1][1]+3}, | |
| 791 {sample_buffer[2][0]+3, sample_buffer[2][1]+3}}; | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
792 |
| 1593 | 793 s->run_index=0; |
| 794 | |
| 795 memset(sample_buffer, 0, sizeof(sample_buffer)); | |
| 796 | |
| 797 for(y=0; y<h; y++){ | |
| 798 for(p=0; p<3; p++){ | |
| 799 int_fast16_t *temp= sample[p][0]; //FIXME try a normal buffer | |
| 800 | |
| 801 sample[p][0]= sample[p][1]; | |
| 802 sample[p][1]= temp; | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
803 |
| 1593 | 804 sample[p][1][-1]= sample[p][0][0 ]; |
| 805 sample[p][0][ w]= sample[p][0][w-1]; | |
| 806 decode_line(s, w, sample[p], FFMIN(p, 1), 9); | |
| 807 } | |
| 808 for(x=0; x<w; x++){ | |
| 809 int g= sample[0][1][x]; | |
| 810 int b= sample[1][1][x]; | |
| 811 int r= sample[2][1][x]; | |
| 1306 | 812 |
| 1593 | 813 // assert(g>=0 && b>=0 && r>=0); |
| 814 // assert(g<256 && b<512 && r<512); | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
815 |
| 1593 | 816 b -= 0x100; |
| 817 r -= 0x100; | |
| 818 g -= (b + r)>>2; | |
| 819 b += g; | |
| 820 r += g; | |
| 821 | |
| 822 src[x + stride*y]= b + (g<<8) + (r<<16); | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
823 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
824 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
825 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
826 |
| 2338 | 827 static int read_quant_table(RangeCoder *c, int16_t *quant_table, int scale){ |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
828 int v; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
829 int i=0; |
| 2338 | 830 uint8_t state[CONTEXT_SIZE]; |
| 831 | |
| 832 memset(state, 128, sizeof(state)); | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
833 |
| 1306 | 834 for(v=0; i<128 ; v++){ |
| 2339 | 835 int len= get_symbol(c, state, 0) + 1; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
836 |
| 1306 | 837 if(len + i > 128) return -1; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
838 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
839 while(len--){ |
| 1306 | 840 quant_table[i] = scale*v; |
| 841 i++; | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
842 //printf("%2d ",v); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
843 //if(i%16==0) printf("\n"); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
844 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
845 } |
| 1306 | 846 |
| 847 for(i=1; i<128; i++){ | |
| 848 quant_table[256-i]= -quant_table[i]; | |
| 849 } | |
| 850 quant_table[128]= -quant_table[127]; | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
851 |
| 1306 | 852 return 2*v - 1; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
853 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
854 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
855 static int read_header(FFV1Context *f){ |
| 2338 | 856 uint8_t state[CONTEXT_SIZE]; |
| 1306 | 857 int i, context_count; |
| 2338 | 858 RangeCoder * const c= &f->c; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
859 |
| 2338 | 860 memset(state, 128, sizeof(state)); |
| 861 | |
| 2339 | 862 f->version= get_symbol(c, state, 0); |
| 863 f->ac= f->avctx->coder_type= get_symbol(c, state, 0); | |
| 864 f->colorspace= get_symbol(c, state, 0); //YUV cs type | |
| 2338 | 865 get_rac(c, state); //no chroma = false |
| 2339 | 866 f->chroma_h_shift= get_symbol(c, state, 0); |
| 867 f->chroma_v_shift= get_symbol(c, state, 0); | |
| 2338 | 868 get_rac(c, state); //transparency plane |
|
1345
daf951f32697
merge U and V statistics, 33% reduction in memory requirement, compression rate better for some files worse for others, worst compression rate loss 0.05%
michaelni
parents:
1337
diff
changeset
|
869 f->plane_count= 2; |
|
1336
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
870 |
| 1593 | 871 if(f->colorspace==0){ |
| 872 switch(16*f->chroma_h_shift + f->chroma_v_shift){ | |
| 873 case 0x00: f->avctx->pix_fmt= PIX_FMT_YUV444P; break; | |
| 874 case 0x10: f->avctx->pix_fmt= PIX_FMT_YUV422P; break; | |
| 875 case 0x11: f->avctx->pix_fmt= PIX_FMT_YUV420P; break; | |
| 876 case 0x20: f->avctx->pix_fmt= PIX_FMT_YUV411P; break; | |
| 877 case 0x33: f->avctx->pix_fmt= PIX_FMT_YUV410P; break; | |
| 878 default: | |
|
1598
932d306bf1dc
av_log() patch by (Michel Bardiaux <mbardiaux at peaktime dot be>)
michael
parents:
1593
diff
changeset
|
879 av_log(f->avctx, AV_LOG_ERROR, "format not supported\n"); |
| 1593 | 880 return -1; |
| 881 } | |
| 882 }else if(f->colorspace==1){ | |
| 883 if(f->chroma_h_shift || f->chroma_v_shift){ | |
|
1598
932d306bf1dc
av_log() patch by (Michel Bardiaux <mbardiaux at peaktime dot be>)
michael
parents:
1593
diff
changeset
|
884 av_log(f->avctx, AV_LOG_ERROR, "chroma subsampling not supported in this colorspace\n"); |
| 1593 | 885 return -1; |
| 886 } | |
| 887 f->avctx->pix_fmt= PIX_FMT_RGBA32; | |
| 888 }else{ | |
|
1598
932d306bf1dc
av_log() patch by (Michel Bardiaux <mbardiaux at peaktime dot be>)
michael
parents:
1593
diff
changeset
|
889 av_log(f->avctx, AV_LOG_ERROR, "colorspace not supported\n"); |
|
1336
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
890 return -1; |
|
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
891 } |
| 1593 | 892 |
|
1336
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
893 //printf("%d %d %d\n", f->chroma_h_shift, f->chroma_v_shift,f->avctx->pix_fmt); |
|
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
894 |
| 1306 | 895 context_count=1; |
| 896 for(i=0; i<5; i++){ | |
| 897 context_count*= read_quant_table(c, f->quant_table[i], context_count); | |
|
1336
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
898 if(context_count < 0){ |
|
1598
932d306bf1dc
av_log() patch by (Michel Bardiaux <mbardiaux at peaktime dot be>)
michael
parents:
1593
diff
changeset
|
899 av_log(f->avctx, AV_LOG_ERROR, "read_quant_table error\n"); |
|
1336
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
900 return -1; |
|
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
901 } |
| 1306 | 902 } |
| 903 context_count= (context_count+1)/2; | |
| 904 | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
905 for(i=0; i<f->plane_count; i++){ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
906 PlaneContext * const p= &f->plane[i]; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
907 |
| 1306 | 908 p->context_count= context_count; |
| 909 | |
| 910 if(f->ac){ | |
| 911 if(!p->state) p->state= av_malloc(CONTEXT_SIZE*p->context_count*sizeof(uint8_t)); | |
| 912 }else{ | |
| 913 if(!p->vlc_state) p->vlc_state= av_malloc(p->context_count*sizeof(VlcState)); | |
| 914 } | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
915 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
916 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
917 return 0; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
918 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
919 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
920 static int decode_init(AVCodecContext *avctx) |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
921 { |
| 1306 | 922 // FFV1Context *s = avctx->priv_data; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
923 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
924 common_init(avctx); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
925 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
926 return 0; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
927 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
928 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
929 static int decode_frame(AVCodecContext *avctx, void *data, int *data_size, uint8_t *buf, int buf_size){ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
930 FFV1Context *f = avctx->priv_data; |
| 2338 | 931 RangeCoder * const c= &f->c; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
932 const int width= f->width; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
933 const int height= f->height; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
934 AVFrame * const p= &f->picture; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
935 int bytes_read; |
| 2338 | 936 uint8_t keystate= 128; |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
937 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
938 AVFrame *picture = data; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
939 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
940 /* no supplementary picture */ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
941 if (buf_size == 0) |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
942 return 0; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
943 |
| 2338 | 944 ff_init_range_decoder(c, buf, buf_size); |
| 945 ff_build_rac_states(c, 0.05*(1LL<<32), 256-8); | |
|
1908
e20fd60b215c
h264 - progressive I frame CABAC support patch by (Laurent Aimar <fenrir at via dot ecp dot fr>)
michael
parents:
1786
diff
changeset
|
946 |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
947 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
948 p->pict_type= FF_I_TYPE; //FIXME I vs. P |
| 2338 | 949 if(get_rac(c, &keystate)){ |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
950 p->key_frame= 1; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
951 read_header(f); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
952 clear_state(f); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
953 }else{ |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
954 p->key_frame= 0; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
955 } |
|
1336
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
956 |
|
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
957 p->reference= 0; |
|
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
958 if(avctx->get_buffer(avctx, p) < 0){ |
|
1598
932d306bf1dc
av_log() patch by (Michel Bardiaux <mbardiaux at peaktime dot be>)
michael
parents:
1593
diff
changeset
|
959 av_log(avctx, AV_LOG_ERROR, "get_buffer() failed\n"); |
|
1336
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
960 return -1; |
|
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
961 } |
|
c16ac5b7ac79
20% less memory needed for 8bit AC state (worst compression rate loss was 0.2%, all other files had <=0.1% loss)
michaelni
parents:
1325
diff
changeset
|
962 |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
963 if(avctx->debug&FF_DEBUG_PICT_INFO) |
|
1598
932d306bf1dc
av_log() patch by (Michel Bardiaux <mbardiaux at peaktime dot be>)
michael
parents:
1593
diff
changeset
|
964 av_log(avctx, AV_LOG_ERROR, "keyframe:%d coder:%d\n", p->key_frame, f->ac); |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
965 |
| 1306 | 966 if(!f->ac){ |
| 2338 | 967 bytes_read = c->bytestream - c->bytestream_start - 1; |
| 968 if(bytes_read ==0) av_log(avctx, AV_LOG_ERROR, "error at end of AC stream\n"); //FIXME | |
| 1306 | 969 //printf("pos=%d\n", bytes_read); |
| 970 init_get_bits(&f->gb, buf + bytes_read, buf_size - bytes_read); | |
| 1453 | 971 } else { |
| 972 bytes_read = 0; /* avoid warning */ | |
| 1306 | 973 } |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
974 |
| 1593 | 975 if(f->colorspace==0){ |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
976 const int chroma_width = -((-width )>>f->chroma_h_shift); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
977 const int chroma_height= -((-height)>>f->chroma_v_shift); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
978 decode_plane(f, p->data[0], width, height, p->linesize[0], 0); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
979 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
980 decode_plane(f, p->data[1], chroma_width, chroma_height, p->linesize[1], 1); |
|
1345
daf951f32697
merge U and V statistics, 33% reduction in memory requirement, compression rate better for some files worse for others, worst compression rate loss 0.05%
michaelni
parents:
1337
diff
changeset
|
981 decode_plane(f, p->data[2], chroma_width, chroma_height, p->linesize[2], 1); |
| 1593 | 982 }else{ |
| 983 decode_rgb_frame(f, (uint32_t*)p->data[0], width, height, p->linesize[0]/4); | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
984 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
985 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
986 emms_c(); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
987 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
988 f->picture_number++; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
989 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
990 *picture= *p; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
991 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
992 avctx->release_buffer(avctx, p); //FIXME |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
993 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
994 *data_size = sizeof(AVFrame); |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
995 |
| 1306 | 996 if(f->ac){ |
| 2338 | 997 bytes_read= c->bytestream - c->bytestream_start - 1; |
|
1598
932d306bf1dc
av_log() patch by (Michel Bardiaux <mbardiaux at peaktime dot be>)
michael
parents:
1593
diff
changeset
|
998 if(bytes_read ==0) av_log(f->avctx, AV_LOG_ERROR, "error at end of frame\n"); |
| 1306 | 999 }else{ |
| 1000 bytes_read+= (get_bits_count(&f->gb)+7)/8; | |
| 1001 } | |
| 1002 | |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1003 return bytes_read; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1004 } |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1005 |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1006 AVCodec ffv1_decoder = { |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1007 "ffv1", |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1008 CODEC_TYPE_VIDEO, |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1009 CODEC_ID_FFV1, |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1010 sizeof(FFV1Context), |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1011 decode_init, |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1012 NULL, |
| 1994 | 1013 NULL, |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1014 decode_frame, |
|
1302
c41f51b5d5d6
reducing memory consumption (reducing number of contexts and other stuff, no noticeable loss in compression rate)
michaelni
parents:
1300
diff
changeset
|
1015 CODEC_CAP_DR1 /*| CODEC_CAP_DRAW_HORIZ_BAND*/, |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1016 NULL |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1017 }; |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1018 |
| 1325 | 1019 #ifdef CONFIG_ENCODERS |
|
1300
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1020 AVCodec ffv1_encoder = { |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1021 "ffv1", |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1022 CODEC_TYPE_VIDEO, |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1023 CODEC_ID_FFV1, |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1024 sizeof(FFV1Context), |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1025 encode_init, |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1026 encode_frame, |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1027 encode_end, |
|
e18667d1e94d
FFV1 codec (our very simple lossless intra only codec, compresses much better then huffyuv)
michaelni
parents:
diff
changeset
|
1028 }; |
| 1325 | 1029 #endif |
