2 * Copyright (C) <1999> Erik Walthinsen <omega@cse.ogi.edu>
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Library General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Library General Public License for more details.
14 * You should have received a copy of the GNU Library General Public
15 * License along with this library; if not, write to the
16 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17 * Boston, MA 02111-1307, USA.
26 /*#define DEBUG_ENABLED*/
27 #include "gstjpegdec.h"
28 #include <gst/video/video.h>
30 /* elementfactory information */
31 GstElementDetails gst_jpegdec_details = {
33 "Codec/Decoder/Image",
34 "Decode images from JPEG format",
35 "Wim Taymans <wim.taymans@tvd.be>",
38 /* JpegDec signals and args */
49 static void gst_jpegdec_base_init (gpointer g_class);
50 static void gst_jpegdec_class_init (GstJpegDec *klass);
51 static void gst_jpegdec_init (GstJpegDec *jpegdec);
53 static void gst_jpegdec_chain (GstPad *pad, GstData *_data);
54 static GstPadLinkReturn
55 gst_jpegdec_link (GstPad *pad, const GstCaps *caps);
57 static GstElementClass *parent_class = NULL;
58 /*static guint gst_jpegdec_signals[LAST_SIGNAL] = { 0 }; */
61 gst_jpegdec_get_type(void) {
62 static GType jpegdec_type = 0;
65 static const GTypeInfo jpegdec_info = {
67 gst_jpegdec_base_init,
69 (GClassInitFunc)gst_jpegdec_class_init,
74 (GInstanceInitFunc)gst_jpegdec_init,
76 jpegdec_type = g_type_register_static(GST_TYPE_ELEMENT, "GstJpegDec", &jpegdec_info, 0);
81 static GstStaticPadTemplate gst_jpegdec_src_pad_template =
82 GST_STATIC_PAD_TEMPLATE (
86 GST_STATIC_CAPS (GST_VIDEO_CAPS_YUV("I420"))
89 static GstStaticPadTemplate gst_jpegdec_sink_pad_template =
90 GST_STATIC_PAD_TEMPLATE (
94 GST_STATIC_CAPS ("image/jpeg, "
95 "width = (int) [ 16, 4096 ], "
96 "height = (int) [ 16, 4096 ], "
97 "framerate = (double) [ 1, MAX ]"
102 gst_jpegdec_base_init (gpointer g_class)
104 GstElementClass *element_class = GST_ELEMENT_CLASS (g_class);
106 gst_element_class_add_pad_template (element_class,
107 gst_static_pad_template_get (&gst_jpegdec_src_pad_template));
108 gst_element_class_add_pad_template (element_class,
109 gst_static_pad_template_get (&gst_jpegdec_sink_pad_template));
110 gst_element_class_set_details (element_class, &gst_jpegdec_details);
114 gst_jpegdec_class_init (GstJpegDec *klass)
116 GstElementClass *gstelement_class;
118 gstelement_class = (GstElementClass*)klass;
120 parent_class = g_type_class_ref(GST_TYPE_ELEMENT);
124 gst_jpegdec_init_source (j_decompress_ptr cinfo)
126 GST_DEBUG ("gst_jpegdec_chain: init_source");
129 gst_jpegdec_fill_input_buffer (j_decompress_ptr cinfo)
131 GST_DEBUG ("gst_jpegdec_chain: fill_input_buffer");
136 gst_jpegdec_skip_input_data (j_decompress_ptr cinfo, glong num_bytes)
138 GST_DEBUG ("gst_jpegdec_chain: skip_input_data");
142 gst_jpegdec_resync_to_restart (j_decompress_ptr cinfo, gint desired)
144 GST_DEBUG ("gst_jpegdec_chain: resync_to_start");
149 gst_jpegdec_term_source (j_decompress_ptr cinfo)
151 GST_DEBUG ("gst_jpegdec_chain: term_source");
155 gst_jpegdec_init (GstJpegDec *jpegdec)
157 GST_DEBUG ("gst_jpegdec_init: initializing");
158 /* create the sink and src pads */
160 jpegdec->sinkpad = gst_pad_new_from_template (
161 gst_static_pad_template_get (&gst_jpegdec_sink_pad_template), "sink");
162 gst_element_add_pad(GST_ELEMENT(jpegdec),jpegdec->sinkpad);
163 gst_pad_set_chain_function(jpegdec->sinkpad,gst_jpegdec_chain);
164 gst_pad_set_link_function(jpegdec->sinkpad, gst_jpegdec_link);
166 jpegdec->srcpad = gst_pad_new_from_template (
167 gst_static_pad_template_get (&gst_jpegdec_src_pad_template), "src");
168 gst_pad_use_explicit_caps (jpegdec->srcpad);
169 gst_element_add_pad(GST_ELEMENT(jpegdec),jpegdec->srcpad);
171 /* initialize the jpegdec decoder state */
172 jpegdec->next_time = 0;
174 /* reset the initial video state */
175 jpegdec->format = -1;
177 jpegdec->height = -1;
179 jpegdec->line[0] = NULL;
180 jpegdec->line[1] = NULL;
181 jpegdec->line[2] = NULL;
184 memset(&jpegdec->cinfo, 0, sizeof(jpegdec->cinfo));
185 memset(&jpegdec->jerr, 0, sizeof(jpegdec->jerr));
186 jpegdec->cinfo.err = jpeg_std_error(&jpegdec->jerr);
187 jpeg_create_decompress(&jpegdec->cinfo);
189 jpegdec->jsrc.init_source = gst_jpegdec_init_source;
190 jpegdec->jsrc.fill_input_buffer = gst_jpegdec_fill_input_buffer;
191 jpegdec->jsrc.skip_input_data = gst_jpegdec_skip_input_data;
192 jpegdec->jsrc.resync_to_restart = gst_jpegdec_resync_to_restart;
193 jpegdec->jsrc.term_source = gst_jpegdec_term_source;
194 jpegdec->cinfo.src = &jpegdec->jsrc;
198 static GstPadLinkReturn
199 gst_jpegdec_link (GstPad *pad, const GstCaps *caps)
201 GstJpegDec *jpegdec = GST_JPEGDEC (gst_pad_get_parent (pad));
202 GstStructure *structure;
205 structure = gst_caps_get_structure (caps, 0);
207 gst_structure_get_double (structure, "framerate", &jpegdec->fps);
208 gst_structure_get_int (structure, "width", &jpegdec->width);
209 gst_structure_get_int (structure, "height", &jpegdec->height);
211 srccaps = gst_caps_new_simple ("video/x-raw-yuv",
212 "format", GST_TYPE_FOURCC, GST_MAKE_FOURCC ('I','4','2','0'),
213 "width", G_TYPE_INT, jpegdec->width,
214 "height", G_TYPE_INT, jpegdec->height,
215 "framerate", G_TYPE_DOUBLE, jpegdec->fps,
218 /* at this point, we're pretty sure that this will be the output
219 * format, so we'll set it. */
220 gst_pad_set_explicit_caps (jpegdec->srcpad, srccaps);
222 return GST_PAD_LINK_OK;
225 /* shamelessly ripped from jpegutils.c in mjpegtools */
226 static void add_huff_table (j_decompress_ptr dinfo,
228 const UINT8 *bits, const UINT8 *val)
229 /* Define a Huffman table */
233 if (*htblptr == NULL)
234 *htblptr = jpeg_alloc_huff_table((j_common_ptr) dinfo);
236 /* Copy the number-of-symbols-of-each-code-length counts */
237 memcpy((*htblptr)->bits, bits, sizeof((*htblptr)->bits));
239 /* Validate the counts. We do this here mainly so we can copy the right
240 * number of symbols from the val[] array, without risking marching off
241 * the end of memory. jchuff.c will do a more thorough test later.
244 for (len = 1; len <= 16; len++)
245 nsymbols += bits[len];
246 if (nsymbols < 1 || nsymbols > 256)
247 g_error("jpegutils.c: add_huff_table failed badly. ");
249 memcpy((*htblptr)->huffval, val, nsymbols * sizeof(UINT8));
254 static void std_huff_tables (j_decompress_ptr dinfo)
255 /* Set up the standard Huffman tables (cf. JPEG standard section K.3) */
256 /* IMPORTANT: these are only valid for 8-bit data precision! */
258 static const UINT8 bits_dc_luminance[17] =
259 { /* 0-base */ 0, 0, 1, 5, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0 };
260 static const UINT8 val_dc_luminance[] =
261 { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11 };
263 static const UINT8 bits_dc_chrominance[17] =
264 { /* 0-base */ 0, 0, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0 };
265 static const UINT8 val_dc_chrominance[] =
266 { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11 };
268 static const UINT8 bits_ac_luminance[17] =
269 { /* 0-base */ 0, 0, 2, 1, 3, 3, 2, 4, 3, 5, 5, 4, 4, 0, 0, 1, 0x7d };
270 static const UINT8 val_ac_luminance[] =
271 { 0x01, 0x02, 0x03, 0x00, 0x04, 0x11, 0x05, 0x12,
272 0x21, 0x31, 0x41, 0x06, 0x13, 0x51, 0x61, 0x07,
273 0x22, 0x71, 0x14, 0x32, 0x81, 0x91, 0xa1, 0x08,
274 0x23, 0x42, 0xb1, 0xc1, 0x15, 0x52, 0xd1, 0xf0,
275 0x24, 0x33, 0x62, 0x72, 0x82, 0x09, 0x0a, 0x16,
276 0x17, 0x18, 0x19, 0x1a, 0x25, 0x26, 0x27, 0x28,
277 0x29, 0x2a, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39,
278 0x3a, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48, 0x49,
279 0x4a, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, 0x59,
280 0x5a, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68, 0x69,
281 0x6a, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, 0x79,
282 0x7a, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, 0x89,
283 0x8a, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98,
284 0x99, 0x9a, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7,
285 0xa8, 0xa9, 0xaa, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6,
286 0xb7, 0xb8, 0xb9, 0xba, 0xc2, 0xc3, 0xc4, 0xc5,
287 0xc6, 0xc7, 0xc8, 0xc9, 0xca, 0xd2, 0xd3, 0xd4,
288 0xd5, 0xd6, 0xd7, 0xd8, 0xd9, 0xda, 0xe1, 0xe2,
289 0xe3, 0xe4, 0xe5, 0xe6, 0xe7, 0xe8, 0xe9, 0xea,
290 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7, 0xf8,
293 static const UINT8 bits_ac_chrominance[17] =
294 { /* 0-base */ 0, 0, 2, 1, 2, 4, 4, 3, 4, 7, 5, 4, 4, 0, 1, 2, 0x77 };
295 static const UINT8 val_ac_chrominance[] =
296 { 0x00, 0x01, 0x02, 0x03, 0x11, 0x04, 0x05, 0x21,
297 0x31, 0x06, 0x12, 0x41, 0x51, 0x07, 0x61, 0x71,
298 0x13, 0x22, 0x32, 0x81, 0x08, 0x14, 0x42, 0x91,
299 0xa1, 0xb1, 0xc1, 0x09, 0x23, 0x33, 0x52, 0xf0,
300 0x15, 0x62, 0x72, 0xd1, 0x0a, 0x16, 0x24, 0x34,
301 0xe1, 0x25, 0xf1, 0x17, 0x18, 0x19, 0x1a, 0x26,
302 0x27, 0x28, 0x29, 0x2a, 0x35, 0x36, 0x37, 0x38,
303 0x39, 0x3a, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48,
304 0x49, 0x4a, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58,
305 0x59, 0x5a, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68,
306 0x69, 0x6a, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78,
307 0x79, 0x7a, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87,
308 0x88, 0x89, 0x8a, 0x92, 0x93, 0x94, 0x95, 0x96,
309 0x97, 0x98, 0x99, 0x9a, 0xa2, 0xa3, 0xa4, 0xa5,
310 0xa6, 0xa7, 0xa8, 0xa9, 0xaa, 0xb2, 0xb3, 0xb4,
311 0xb5, 0xb6, 0xb7, 0xb8, 0xb9, 0xba, 0xc2, 0xc3,
312 0xc4, 0xc5, 0xc6, 0xc7, 0xc8, 0xc9, 0xca, 0xd2,
313 0xd3, 0xd4, 0xd5, 0xd6, 0xd7, 0xd8, 0xd9, 0xda,
314 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7, 0xe8, 0xe9,
315 0xea, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7, 0xf8,
318 add_huff_table(dinfo, &dinfo->dc_huff_tbl_ptrs[0],
319 bits_dc_luminance, val_dc_luminance);
320 add_huff_table(dinfo, &dinfo->ac_huff_tbl_ptrs[0],
321 bits_ac_luminance, val_ac_luminance);
322 add_huff_table(dinfo, &dinfo->dc_huff_tbl_ptrs[1],
323 bits_dc_chrominance, val_dc_chrominance);
324 add_huff_table(dinfo, &dinfo->ac_huff_tbl_ptrs[1],
325 bits_ac_chrominance, val_ac_chrominance);
330 static void guarantee_huff_tables(j_decompress_ptr dinfo)
332 if ( (dinfo->dc_huff_tbl_ptrs[0] == NULL) &&
333 (dinfo->dc_huff_tbl_ptrs[1] == NULL) &&
334 (dinfo->ac_huff_tbl_ptrs[0] == NULL) &&
335 (dinfo->ac_huff_tbl_ptrs[1] == NULL) ) {
337 "Generating standard Huffman tables for this frame.");
338 std_huff_tables(dinfo);
343 gst_jpegdec_chain (GstPad *pad, GstData *_data)
345 GstBuffer *buf = GST_BUFFER (_data);
347 guchar *data, *outdata;
348 gulong size, outsize;
351 gint width, height, width2;
356 g_return_if_fail(pad != NULL);
357 g_return_if_fail(GST_IS_PAD(pad));
358 g_return_if_fail(buf != NULL);
359 /*g_return_if_fail(GST_IS_BUFFER(buf));*/
361 jpegdec = GST_JPEGDEC (GST_OBJECT_PARENT (pad));
363 if (!GST_PAD_IS_LINKED (jpegdec->srcpad)) {
364 gst_buffer_unref (buf);
368 data = (guchar *)GST_BUFFER_DATA(buf);
369 size = GST_BUFFER_SIZE(buf);
370 GST_DEBUG ("gst_jpegdec_chain: got buffer of %ld bytes in '%s'",size,
371 GST_OBJECT_NAME (jpegdec));
373 jpegdec->jsrc.next_input_byte = data;
374 jpegdec->jsrc.bytes_in_buffer = size;
377 GST_DEBUG ("gst_jpegdec_chain: reading header %08lx", *(gulong *)data);
378 jpeg_read_header(&jpegdec->cinfo, TRUE);
380 r_h = jpegdec->cinfo.cur_comp_info[0]->h_samp_factor;
381 r_v = jpegdec->cinfo.cur_comp_info[0]->v_samp_factor;
383 /*g_print ("%d %d\n", r_h, r_v);*/
384 /*g_print ("%d %d\n", jpegdec->cinfo.cur_comp_info[1]->h_samp_factor, jpegdec->cinfo.cur_comp_info[1]->v_samp_factor);*/
385 /*g_print ("%d %d\n", jpegdec->cinfo.cur_comp_info[2]->h_samp_factor, jpegdec->cinfo.cur_comp_info[2]->v_samp_factor);*/
387 jpegdec->cinfo.do_fancy_upsampling = FALSE;
388 jpegdec->cinfo.do_block_smoothing = FALSE;
389 jpegdec->cinfo.out_color_space = JCS_YCbCr;
390 jpegdec->cinfo.dct_method = JDCT_IFAST;
391 jpegdec->cinfo.raw_data_out = TRUE;
392 GST_DEBUG ("gst_jpegdec_chain: starting decompress");
393 guarantee_huff_tables(&jpegdec->cinfo);
394 jpeg_start_decompress(&jpegdec->cinfo);
395 width = jpegdec->cinfo.output_width;
396 height = jpegdec->cinfo.output_height;
397 GST_DEBUG ("gst_jpegdec_chain: width %d, height %d", width, height);
399 outbuf = gst_buffer_new();
400 outsize = GST_BUFFER_SIZE(outbuf) = width*height +
402 outdata = GST_BUFFER_DATA(outbuf) = g_malloc(outsize);
403 GST_BUFFER_TIMESTAMP(outbuf) = GST_BUFFER_TIMESTAMP(buf);
405 if (jpegdec->height != height || jpegdec->line[0] == NULL) {
408 jpegdec->line[0] = g_realloc(jpegdec->line[0], height*sizeof(char*));
409 jpegdec->line[1] = g_realloc(jpegdec->line[1], height*sizeof(char*));
410 jpegdec->line[2] = g_realloc(jpegdec->line[2], height*sizeof(char*));
411 jpegdec->height = height;
413 caps = gst_caps_new_simple ("video/x-raw-yuv",
414 "format", GST_TYPE_FOURCC, GST_MAKE_FOURCC ('I','4','2','0'),
415 "width", G_TYPE_INT, width,
416 "height", G_TYPE_INT, height,
417 "framerate", G_TYPE_DOUBLE, jpegdec->fps,
419 gst_pad_set_explicit_caps (jpegdec->srcpad, caps);
420 gst_caps_free (caps);
423 /* mind the swap, jpeglib outputs blue chroma first */
425 base[1] = base[0]+width*height;
426 base[2] = base[1]+width*height/4;
430 GST_DEBUG ("gst_jpegdec_chain: decompressing %u", jpegdec->cinfo.rec_outbuf_height);
431 for (i = 0; i < height; i += r_v*DCTSIZE) {
432 for (j=0, k=0; j< (r_v*DCTSIZE); j += r_v, k++) {
433 jpegdec->line[0][j] = base[0]; base[0] += width;
435 jpegdec->line[0][j+1] = base[0]; base[0] += width;
437 jpegdec->line[1][k] = base[1];
438 jpegdec->line[2][k] = base[2];
439 if (r_v == 2 || k&1) {
440 base[1] += width2; base[2] += width2;
443 /*g_print ("%d\n", jpegdec->cinfo.output_scanline);*/
444 jpeg_read_raw_data(&jpegdec->cinfo, jpegdec->line, r_v*DCTSIZE);
447 GST_DEBUG ("gst_jpegdec_chain: decompressing finished");
448 jpeg_finish_decompress(&jpegdec->cinfo);
450 GST_DEBUG ("gst_jpegdec_chain: sending buffer");
451 gst_pad_push(jpegdec->srcpad, GST_DATA (outbuf));
453 gst_buffer_unref(buf);