Mercurial > libavcodec.hg
comparison lclenc.c @ 5294:e21873a1c00b libavcodec
split lcl.c into lcldec.c, lclenc.c, lcl.h
author | mru |
---|---|
date | Thu, 12 Jul 2007 22:40:33 +0000 |
parents | lcl.c@2b72f9bc4f06 |
children | 48759bfbd073 |
comparison
equal
deleted
inserted
replaced
5293:de5b524db473 | 5294:e21873a1c00b |
---|---|
1 /* | |
2 * LCL (LossLess Codec Library) Codec | |
3 * Copyright (c) 2002-2004 Roberto Togni | |
4 * | |
5 * This file is part of FFmpeg. | |
6 * | |
7 * FFmpeg is free software; you can redistribute it and/or | |
8 * modify it under the terms of the GNU Lesser General Public | |
9 * License as published by the Free Software Foundation; either | |
10 * version 2.1 of the License, or (at your option) any later version. | |
11 * | |
12 * FFmpeg is distributed in the hope that it will be useful, | |
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
15 * Lesser General Public License for more details. | |
16 * | |
17 * You should have received a copy of the GNU Lesser General Public | |
18 * License along with FFmpeg; if not, write to the Free Software | |
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | |
20 */ | |
21 | |
22 /** | |
23 * @file lcl.c | |
24 * LCL (LossLess Codec Library) Video Codec | |
25 * Decoder for MSZH and ZLIB codecs | |
26 * Experimental encoder for ZLIB RGB24 | |
27 * | |
28 * Fourcc: MSZH, ZLIB | |
29 * | |
30 * Original Win32 dll: | |
31 * Ver2.23 By Kenji Oshima 2000.09.20 | |
32 * avimszh.dll, avizlib.dll | |
33 * | |
34 * A description of the decoding algorithm can be found here: | |
35 * http://www.pcisys.net/~melanson/codecs | |
36 * | |
37 * Supports: BGR24 (RGB 24bpp) | |
38 * | |
39 */ | |
40 | |
41 #include <stdio.h> | |
42 #include <stdlib.h> | |
43 | |
44 #include "avcodec.h" | |
45 #include "bitstream.h" | |
46 #include "lcl.h" | |
47 | |
48 #ifdef CONFIG_ZLIB | |
49 #include <zlib.h> | |
50 #endif | |
51 | |
52 /* | |
53 * Decoder context | |
54 */ | |
55 typedef struct LclEncContext { | |
56 | |
57 AVCodecContext *avctx; | |
58 AVFrame pic; | |
59 PutBitContext pb; | |
60 | |
61 // Image type | |
62 int imgtype; | |
63 // Compression type | |
64 int compression; | |
65 // Flags | |
66 int flags; | |
67 // Decompressed data size | |
68 unsigned int decomp_size; | |
69 // Maximum compressed data size | |
70 unsigned int max_comp_size; | |
71 // Compression buffer | |
72 unsigned char* comp_buf; | |
73 #ifdef CONFIG_ZLIB | |
74 z_stream zstream; | |
75 #endif | |
76 } LclEncContext; | |
77 | |
78 /* | |
79 * | |
80 * Encode a frame | |
81 * | |
82 */ | |
83 static int encode_frame(AVCodecContext *avctx, unsigned char *buf, int buf_size, void *data){ | |
84 LclEncContext *c = avctx->priv_data; | |
85 AVFrame *pict = data; | |
86 AVFrame * const p = &c->pic; | |
87 int i; | |
88 int zret; // Zlib return code | |
89 | |
90 #ifndef CONFIG_ZLIB | |
91 av_log(avctx, AV_LOG_ERROR, "Zlib support not compiled in.\n"); | |
92 return -1; | |
93 #else | |
94 | |
95 init_put_bits(&c->pb, buf, buf_size); | |
96 | |
97 *p = *pict; | |
98 p->pict_type= FF_I_TYPE; | |
99 p->key_frame= 1; | |
100 | |
101 if(avctx->pix_fmt != PIX_FMT_BGR24){ | |
102 av_log(avctx, AV_LOG_ERROR, "Format not supported!\n"); | |
103 return -1; | |
104 } | |
105 | |
106 zret = deflateReset(&(c->zstream)); | |
107 if (zret != Z_OK) { | |
108 av_log(avctx, AV_LOG_ERROR, "Deflate reset error: %d\n", zret); | |
109 return -1; | |
110 } | |
111 c->zstream.next_out = c->comp_buf; | |
112 c->zstream.avail_out = c->max_comp_size; | |
113 | |
114 for(i = avctx->height - 1; i >= 0; i--) { | |
115 c->zstream.next_in = p->data[0]+p->linesize[0]*i; | |
116 c->zstream.avail_in = avctx->width*3; | |
117 zret = deflate(&(c->zstream), Z_NO_FLUSH); | |
118 if (zret != Z_OK) { | |
119 av_log(avctx, AV_LOG_ERROR, "Deflate error: %d\n", zret); | |
120 return -1; | |
121 } | |
122 } | |
123 zret = deflate(&(c->zstream), Z_FINISH); | |
124 if (zret != Z_STREAM_END) { | |
125 av_log(avctx, AV_LOG_ERROR, "Deflate error: %d\n", zret); | |
126 return -1; | |
127 } | |
128 | |
129 for (i = 0; i < c->zstream.total_out; i++) | |
130 put_bits(&c->pb, 8, c->comp_buf[i]); | |
131 flush_put_bits(&c->pb); | |
132 | |
133 return c->zstream.total_out; | |
134 #endif | |
135 } | |
136 | |
137 /* | |
138 * | |
139 * Init lcl encoder | |
140 * | |
141 */ | |
142 static int encode_init(AVCodecContext *avctx) | |
143 { | |
144 LclEncContext *c = avctx->priv_data; | |
145 int zret; // Zlib return code | |
146 | |
147 #ifndef CONFIG_ZLIB | |
148 av_log(avctx, AV_LOG_ERROR, "Zlib support not compiled.\n"); | |
149 return 1; | |
150 #else | |
151 | |
152 c->avctx= avctx; | |
153 | |
154 assert(avctx->width && avctx->height); | |
155 | |
156 avctx->extradata= av_mallocz(8); | |
157 avctx->coded_frame= &c->pic; | |
158 | |
159 // Will be user settable someday | |
160 c->compression = 6; | |
161 c->flags = 0; | |
162 | |
163 switch(avctx->pix_fmt){ | |
164 case PIX_FMT_BGR24: | |
165 c->imgtype = IMGTYPE_RGB24; | |
166 c->decomp_size = avctx->width * avctx->height * 3; | |
167 avctx->bits_per_sample= 24; | |
168 break; | |
169 default: | |
170 av_log(avctx, AV_LOG_ERROR, "Format %d not supported\n", avctx->pix_fmt); | |
171 return -1; | |
172 } | |
173 | |
174 ((uint8_t*)avctx->extradata)[0]= 4; | |
175 ((uint8_t*)avctx->extradata)[1]= 0; | |
176 ((uint8_t*)avctx->extradata)[2]= 0; | |
177 ((uint8_t*)avctx->extradata)[3]= 0; | |
178 ((uint8_t*)avctx->extradata)[4]= c->imgtype; | |
179 ((uint8_t*)avctx->extradata)[5]= c->compression; | |
180 ((uint8_t*)avctx->extradata)[6]= c->flags; | |
181 ((uint8_t*)avctx->extradata)[7]= CODEC_ZLIB; | |
182 c->avctx->extradata_size= 8; | |
183 | |
184 c->zstream.zalloc = Z_NULL; | |
185 c->zstream.zfree = Z_NULL; | |
186 c->zstream.opaque = Z_NULL; | |
187 zret = deflateInit(&(c->zstream), c->compression); | |
188 if (zret != Z_OK) { | |
189 av_log(avctx, AV_LOG_ERROR, "Deflate init error: %d\n", zret); | |
190 return 1; | |
191 } | |
192 | |
193 /* Conservative upper bound taken from zlib v1.2.1 source */ | |
194 c->max_comp_size = c->decomp_size + ((c->decomp_size + 7) >> 3) + | |
195 ((c->decomp_size + 63) >> 6) + 11; | |
196 if ((c->comp_buf = av_malloc(c->max_comp_size)) == NULL) { | |
197 av_log(avctx, AV_LOG_ERROR, "Can't allocate compression buffer.\n"); | |
198 return 1; | |
199 } | |
200 | |
201 return 0; | |
202 #endif | |
203 } | |
204 | |
205 /* | |
206 * | |
207 * Uninit lcl encoder | |
208 * | |
209 */ | |
210 static int encode_end(AVCodecContext *avctx) | |
211 { | |
212 LclEncContext *c = avctx->priv_data; | |
213 | |
214 av_freep(&avctx->extradata); | |
215 av_freep(&c->comp_buf); | |
216 #ifdef CONFIG_ZLIB | |
217 deflateEnd(&(c->zstream)); | |
218 #endif | |
219 | |
220 return 0; | |
221 } | |
222 | |
223 AVCodec zlib_encoder = { | |
224 "zlib", | |
225 CODEC_TYPE_VIDEO, | |
226 CODEC_ID_ZLIB, | |
227 sizeof(LclEncContext), | |
228 encode_init, | |
229 encode_frame, | |
230 encode_end, | |
231 }; |