From d5ad427c732f6f398cfc9c1d9d4b1fe4298b543a Mon Sep 17 00:00:00 2001 From: Edgard Lima Date: Fri, 30 Nov 2007 18:30:12 +0000 Subject: Muxer writes (in jpeg only) whole EXIF and XMP chunks sent as tags. Original commit message from CVS: Muxer writes (in jpeg only) whole EXIF and XMP chunks sent as tags. --- ChangeLog | 18 ++++++++ ext/metadata/gstmetadatamux.c | 59 +++++++++++++----------- ext/metadata/gstmetadatamux.h | 3 +- ext/metadata/gstmetadataparse.c | 14 +++--- ext/metadata/gstmetadataparse.h | 1 - ext/metadata/metadataexif.c | 39 +++++++++++++--- ext/metadata/metadataexif.h | 2 +- ext/metadata/metadataiptc.c | 16 +++---- ext/metadata/metadataiptc.h | 2 +- ext/metadata/metadatamuxjpeg.c | 75 ++++++++++++++++++++----------- ext/metadata/metadatamuxpng.c | 97 ++++++---------------------------------- ext/metadata/metadataparsejpeg.c | 3 -- ext/metadata/metadataparsepng.c | 4 +- ext/metadata/metadataxmp.c | 29 ++++++++---- ext/metadata/metadataxmp.h | 2 +- 15 files changed, 187 insertions(+), 177 deletions(-) diff --git a/ChangeLog b/ChangeLog index 3221c42d..24526d23 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,21 @@ +2007-11-30 Edgard Lima + + * ext/metadata/gstmetadatamux.c: + * ext/metadata/gstmetadatamux.h: + * ext/metadata/gstmetadataparse.c: + * ext/metadata/gstmetadataparse.h: + * ext/metadata/metadataexif.c: + * ext/metadata/metadataexif.h: + * ext/metadata/metadataiptc.c: + * ext/metadata/metadataiptc.h: + * ext/metadata/metadatamuxjpeg.c: + * ext/metadata/metadatamuxpng.c: + * ext/metadata/metadataparsejpeg.c: + * ext/metadata/metadataparsepng.c: + * ext/metadata/metadataxmp.c: + * ext/metadata/metadataxmp.h: + Muxer writes (in jpeg only) whole EXIF and XMP chunks sent as tags. + 2007-11-30 Thijs Vermeir * gst/librfb/rfbdecoder.c: diff --git a/ext/metadata/gstmetadatamux.c b/ext/metadata/gstmetadatamux.c index 0900ea91..a31d072f 100644 --- a/ext/metadata/gstmetadatamux.c +++ b/ext/metadata/gstmetadatamux.c @@ -276,6 +276,8 @@ gst_metadata_mux_init (GstMetadataMux * filter, GstMetadataMuxClass * gclass) gst_element_add_pad (GST_ELEMENT (filter), filter->sinkpad); gst_element_add_pad (GST_ELEMENT (filter), filter->srcpad); + + metadataparse_xmp_init (); /* init members */ gst_metadata_mux_init_members (filter); @@ -522,6 +524,12 @@ gst_metadata_mux_sink_event (GstPad * pad, GstEvent * event) } break; case GST_EVENT_TAG: + { + GstTagList *taglist = NULL; + + gst_event_parse_tag (event, &taglist); + gst_tag_list_insert (filter->taglist, taglist, GST_TAG_MERGE_REPLACE); + } break; default: break; @@ -544,6 +552,8 @@ gst_metadata_mux_dispose (GObject * object) gst_metadata_mux_dispose_members (filter); + metadataparse_xmp_dispose (); + G_OBJECT_CLASS (metadata_parent_class)->dispose (object); } @@ -753,27 +763,29 @@ gst_metadata_mux_get_type_name (int img_type) } static void -gst_metadata_update_segment (GstMetadataMux * filter, GstAdapter * adapter, - MetadataChunkType type) +gst_metadata_update_segment (GstMetadataMux * filter, guint8 ** buf, + guint32 * size, MetadataChunkType type) { int i; MetadataChunk *inject = filter->mux_data.inject_chunks.chunk; const gsize inject_len = filter->mux_data.inject_chunks.len; - guint32 size; - if (adapter == NULL) + if (!(buf && size)) goto done; - - size = gst_adapter_available (adapter); - - if (size == 0) + if (*buf == 0) + goto done; + if (*size == 0) goto done; /* calculate the new position off injected chunks */ for (i = 0; i < inject_len; ++i) { if (inject[i].type == type) { - inject[i].size = size; - inject[i].data = (guint8 *) gst_adapter_peek (adapter, inject[i].size); + inject[i].size = *size; + if (inject[i].data) + g_free (inject[i].data); + inject[i].data = *buf; + *size = 0; + *buf = 0; break; } } @@ -791,26 +803,22 @@ gst_metadata_create_chunks_from_tags (GstMetadataMux * filter) GstMessage *msg; GstTagList *taglist; GstEvent *event; + guint8 *buf = NULL; + guint32 size = 0; if (META_DATA_OPTION (filter->mux_data) & META_OPT_EXIF) { - metadatamux_exif_create_chunk_from_tag_list (&filter->mux_data.exif_adapter, - filter->taglist); - gst_metadata_update_segment (filter, filter->mux_data.exif_adapter, - MD_CHUNK_EXIF); + metadatamux_exif_create_chunk_from_tag_list (&buf, &size, filter->taglist); + gst_metadata_update_segment (filter, &buf, &size, MD_CHUNK_EXIF); } if (META_DATA_OPTION (filter->mux_data) & META_OPT_IPTC) { - metadatamux_iptc_create_chunk_from_tag_list (&filter->mux_data.iptc_adapter, - filter->taglist); - gst_metadata_update_segment (filter, filter->mux_data.iptc_adapter, - MD_CHUNK_IPTC); + metadatamux_iptc_create_chunk_from_tag_list (&buf, &size, filter->taglist); + gst_metadata_update_segment (filter, &buf, &size, MD_CHUNK_IPTC); } if (META_DATA_OPTION (filter->mux_data) & META_OPT_XMP) { - metadatamux_xmp_create_chunk_from_tag_list (&filter->mux_data.xmp_adapter, - filter->taglist); - gst_metadata_update_segment (filter, filter->mux_data.xmp_adapter, - MD_CHUNK_XMP); + metadatamux_xmp_create_chunk_from_tag_list (&buf, &size, filter->taglist); + gst_metadata_update_segment (filter, &buf, &size, MD_CHUNK_XMP); } metadata_chunk_array_remove_zero_size (&filter->mux_data.inject_chunks); @@ -900,6 +908,8 @@ gst_metadata_mux_calculate_offsets (GstMetadataMux * filter) gst_metadata_create_chunks_from_tags (filter); + metadata_lazy_update (&filter->mux_data); + bytes_striped = 0; bytes_inject = 0; @@ -940,8 +950,6 @@ gst_metadata_mux_calculate_offsets (GstMetadataMux * filter) } } - metadata_lazy_update (&filter->mux_data); - if (filter->duration_orig) { filter->duration = filter->duration_orig; for (i = 0; i < inject_len; ++i) { @@ -1486,7 +1494,8 @@ inject: } if (inject[i].offset_orig >= offset_orig) { - if (inject[i].offset_orig < offset_orig + size_buf_in + striped_bytes) { + if (inject[i].offset_orig < + offset_orig + size_buf_in + striped_bytes - injected_bytes) { /* insert */ guint32 buf_off = inject[i].offset_orig - offset_orig - striped_so_far + diff --git a/ext/metadata/gstmetadatamux.h b/ext/metadata/gstmetadatamux.h index 8ecbba92..a044ba41 100644 --- a/ext/metadata/gstmetadatamux.h +++ b/ext/metadata/gstmetadatamux.h @@ -79,7 +79,6 @@ struct _GstMetadataMux gboolean iptc; gboolean xmp; - GstTagList *taglist; MetaData mux_data; GstAdapter *adapter_parsing; GstAdapter *adapter_holding; @@ -99,7 +98,7 @@ struct _GstMetadataMux gboolean need_more_data; - gboolean need_send_tag; /* demux still need send tags */ + GstTagList *taglist; gboolean need_calculate_offset; /* mux need to calculate offsets of insert chunks */ }; diff --git a/ext/metadata/gstmetadataparse.c b/ext/metadata/gstmetadataparse.c index dd4771e3..d2f1a945 100644 --- a/ext/metadata/gstmetadataparse.c +++ b/ext/metadata/gstmetadataparse.c @@ -280,6 +280,7 @@ gst_metadata_parse_init (GstMetadataParse * filter, gst_element_add_pad (GST_ELEMENT (filter), filter->sinkpad); gst_element_add_pad (GST_ELEMENT (filter), filter->srcpad); + metadataparse_xmp_init (); /* init members */ gst_metadata_parse_init_members (filter); @@ -548,7 +549,10 @@ gst_metadata_parse_dispose (GObject * object) gst_metadata_parse_dispose_members (filter); + metadataparse_xmp_dispose (); + G_OBJECT_CLASS (metadata_parent_class)->dispose (object); + } static void @@ -572,11 +576,6 @@ gst_metadata_parse_dispose_members (GstMetadataParse * filter) filter->adapter_holding = NULL; } - if (filter->taglist) { - gst_tag_list_free (filter->taglist); - filter->taglist = NULL; - } - if (filter->append_buffer) { gst_buffer_unref (filter->append_buffer); filter->append_buffer = NULL; @@ -596,7 +595,6 @@ gst_metadata_parse_init_members (GstMetadataParse * filter) filter->iptc = TRUE; filter->xmp = TRUE; - filter->taglist = NULL; filter->adapter_parsing = NULL; filter->adapter_holding = NULL; filter->next_offset = 0; @@ -1471,7 +1469,8 @@ inject: } if (inject[i].offset_orig >= offset_orig) { - if (inject[i].offset_orig < offset_orig + size_buf_in + striped_bytes) { + if (inject[i].offset_orig < + offset_orig + size_buf_in + striped_bytes - injected_bytes) { /* insert */ guint32 buf_off = inject[i].offset_orig - offset_orig - striped_so_far + @@ -1734,7 +1733,6 @@ gst_metadata_parse_change_state (GstElement * element, case GST_STATE_CHANGE_NULL_TO_READY: gst_metadata_parse_init_members (filter); filter->adapter_parsing = gst_adapter_new (); - filter->taglist = gst_tag_list_new (); metadata_init (&filter->parse_data, TRUE); break; default: diff --git a/ext/metadata/gstmetadataparse.h b/ext/metadata/gstmetadataparse.h index ca9e7ab4..10a97da8 100644 --- a/ext/metadata/gstmetadataparse.h +++ b/ext/metadata/gstmetadataparse.h @@ -81,7 +81,6 @@ struct _GstMetadataParse gboolean need_send_tag; - GstTagList *taglist; MetaData parse_data; GstAdapter *adapter_parsing; GstAdapter *adapter_holding; diff --git a/ext/metadata/metadataexif.c b/ext/metadata/metadataexif.c index 583be86f..135bedd2 100644 --- a/ext/metadata/metadataexif.c +++ b/ext/metadata/metadataexif.c @@ -64,7 +64,7 @@ metadataparse_exif_tag_list_add (GstTagList * taglist, GstTagMergeMode mode, } void -metadatamux_exif_create_chunk_from_tag_list (GstAdapter ** adapter, +metadatamux_exif_create_chunk_from_tag_list (guint8 ** buf, guint32 * size, GstTagList * taglist) { /* do nothing */ @@ -202,19 +202,46 @@ exif_content_foreach_entry_func (ExifEntry * entry, void *user_data) */ void -metadatamux_exif_create_chunk_from_tag_list (GstAdapter ** adapter, +metadatamux_exif_create_chunk_from_tag_list (guint8 ** buf, guint32 * size, GstTagList * taglist) { - if (adapter == NULL) + ExifData *ed = NULL; + GstBuffer *exif_chunk = NULL; + const GValue *val = NULL; + + if (!(buf && size)) goto done; + if (*buf) { + g_free (*buf); + *buf = NULL; + } + *size = 0; + + val = gst_tag_list_get_value_index (taglist, GST_TAG_EXIF, 0); + if (val) { + exif_chunk = gst_value_get_buffer (val); + if (exif_chunk) { + ed = exif_data_new_from_data (GST_BUFFER_DATA (exif_chunk), + GST_BUFFER_SIZE (exif_chunk)); + } + } - if (*adapter) - g_object_unref (*adapter); + if (!ed) { + ed = exif_data_new (); + exif_data_set_data_type (ed, EXIF_DATA_TYPE_COMPRESSED); + exif_data_fix (ed); + } + + /* FIXME: consider individual tags */ + + exif_data_save_data (ed, buf, size); - *adapter = gst_adapter_new (); done: + if (ed) + exif_data_unref (ed); + return; } diff --git a/ext/metadata/metadataexif.h b/ext/metadata/metadataexif.h index 2fa6380f..cc53c87a 100644 --- a/ext/metadata/metadataexif.h +++ b/ext/metadata/metadataexif.h @@ -55,7 +55,7 @@ metadataparse_exif_tag_list_add (GstTagList * taglist, GstTagMergeMode mode, GstAdapter * adapter, MetadataTagMapping mapping); extern void -metadatamux_exif_create_chunk_from_tag_list (GstAdapter ** adapter, +metadatamux_exif_create_chunk_from_tag_list (guint8 ** buf, guint32 *size, GstTagList * taglist); G_END_DECLS diff --git a/ext/metadata/metadataiptc.c b/ext/metadata/metadataiptc.c index 8c0507a4..7af879ef 100644 --- a/ext/metadata/metadataiptc.c +++ b/ext/metadata/metadataiptc.c @@ -65,7 +65,7 @@ metadataparse_iptc_tag_list_add (GstTagList * taglist, GstTagMergeMode mode, void -metadatamux_iptc_create_chunk_from_tag_list (GstAdapter ** adapter, +metadatamux_iptc_create_chunk_from_tag_list (guint8 ** buf, guint32 * size, GstTagList * taglist) { /* do nothing */ @@ -132,16 +132,16 @@ iptc_data_foreach_dataset_func (IptcDataSet * dataset, void *user_data) } void -metadatamux_iptc_create_chunk_from_tag_list (GstAdapter ** adapter, +metadatamux_iptc_create_chunk_from_tag_list (guint8 ** buf, guint32 * size, GstTagList * taglist) { - if (adapter == NULL) + if (!(buf && size)) goto done; - - if (*adapter) - g_object_unref (*adapter); - - *adapter = gst_adapter_new (); + if (*buf) { + g_free (*buf); + *buf = NULL; + } + *size = 0; done: diff --git a/ext/metadata/metadataiptc.h b/ext/metadata/metadataiptc.h index 0681380b..a8fa6de8 100644 --- a/ext/metadata/metadataiptc.h +++ b/ext/metadata/metadataiptc.h @@ -55,7 +55,7 @@ metadataparse_iptc_tag_list_add (GstTagList * taglist, GstTagMergeMode mode, GstAdapter * adapter, MetadataTagMapping mapping); extern void -metadatamux_iptc_create_chunk_from_tag_list (GstAdapter ** adapter, +metadatamux_iptc_create_chunk_from_tag_list (guint8 ** buf, guint32 *size, GstTagList * taglist); G_END_DECLS diff --git a/ext/metadata/metadatamuxjpeg.c b/ext/metadata/metadatamuxjpeg.c index 15d9d19c..50844a48 100644 --- a/ext/metadata/metadatamuxjpeg.c +++ b/ext/metadata/metadatamuxjpeg.c @@ -54,16 +54,49 @@ metadatamux_jpeg_reading (JpegMuxData * jpeg_data, guint8 ** buf, #define READ(buf, size) ( (size)--, *((buf)++) ) +static void +metadatamux_wrap_chunk (MetadataChunk * chunk, guint8 * buf, guint32 buf_size, + guint8 a, guint8 b) +{ + guint8 *data = g_new (guint8, 4 + buf_size + chunk->size); + + memcpy (data + 4 + buf_size, chunk->data, chunk->size); + g_free (chunk->data); + chunk->data = data; + chunk->size += 4 + buf_size; + data[0] = a; + data[1] = b; + data[2] = (chunk->size - 2) >> 8; + data[3] = (chunk->size - 2) & 0x00FF; + if (buf && buf_size) { + memcpy (data + 4, buf, buf_size); + } +} + void metadatamux_jpeg_lazy_update (JpegMuxData * jpeg_data) { gsize i; for (i = 0; i < jpeg_data->inject_chunks->len; ++i) { - if (jpeg_data->inject_chunks->chunk[i].type == MD_CHUNK_EXIF && - jpeg_data->inject_chunks->chunk[i].size > 0) { - /* zero size chunks should be removed before but we check anyway */ - break; + if (jpeg_data->inject_chunks->chunk[i].size > 0 && + jpeg_data->inject_chunks->chunk[i].data) { + switch (jpeg_data->inject_chunks->chunk[i].type) { + case MD_CHUNK_EXIF: + metadatamux_wrap_chunk (&jpeg_data->inject_chunks->chunk[i], NULL, 0, + 0xFF, 0xE1); + break; + case MD_CHUNK_XMP: + { + static const char XmpHeader[] = "http://ns.adobe.com/xap/1.0/"; + + metadatamux_wrap_chunk (&jpeg_data->inject_chunks->chunk[i], + XmpHeader, sizeof (XmpHeader), 0xFF, 0xE1); + } + break; + default: + break; + } } } if (i == jpeg_data->inject_chunks->len) { @@ -181,21 +214,6 @@ metadatamux_jpeg_reading (JpegMuxData * jpeg_data, guint8 ** buf, mark[1] = READ (*buf, *bufsize); if (mark[0] == 0xFF) { - if (mark[1] == 0xD9) { /* end of image */ - ret = 0; - jpeg_data->state = JPEG_MUX_DONE; - goto done; - } else if (mark[1] == 0xDA) { /* start of scan, lets not look behinf of this */ - ret = 0; - jpeg_data->state = JPEG_MUX_DONE; - goto done; - } - - if (*bufsize < 2) { - *next_size = (*buf - *next_start) + 2; - ret = 1; - goto done; - } chunk_size = READ (*buf, *bufsize) << 8; chunk_size += READ (*buf, *bufsize); @@ -203,27 +221,32 @@ metadatamux_jpeg_reading (JpegMuxData * jpeg_data, guint8 ** buf, if (mark[1] == 0xE0) { /* may be JFIF */ if (chunk_size >= 16) { - if (*bufsize < 14) { - *next_size = (*buf - *next_start) + 14; + if (*bufsize < 5) { + *next_size = (*buf - *next_start) + 5; ret = 1; goto done; } if (0 == memcmp (JfifHeader, *buf, 5)) { jfif_found = TRUE; - /* FIXME: should we fail if not find JFIF */ - /* Yes, I think so */ } + } else { + /* FIXME: should we check if the first chunk is EXIF? */ } } - new_chunk_offset = (*buf - step_buf) + offset - 4; /* maker + size */ + if (!jfif_found) { + ret = -1; + goto done; + } + + new_chunk_offset = 2; /* EXIF will always be in the begining */ memset (&chunk, 0x00, sizeof (MetadataChunk)); - chunk.offset_orig = new_chunk_offset; + chunk.offset_orig = 2; chunk.type = MD_CHUNK_EXIF; metadata_chunk_array_append_sorted (jpeg_data->inject_chunks, &chunk); @@ -232,7 +255,7 @@ metadatamux_jpeg_reading (JpegMuxData * jpeg_data, guint8 ** buf, /* this acation can be canceled with lazy update if no Exif is add */ memset (&chunk, 0x00, sizeof (MetadataChunk)); - chunk.offset_orig = new_chunk_offset; + chunk.offset_orig = 2; chunk.size = chunk_size + 2; /* chunk size plus app marker */ chunk.type = MD_CHUNK_UNKNOWN; diff --git a/ext/metadata/metadatamuxpng.c b/ext/metadata/metadatamuxpng.c index 2f059e3d..afcd380b 100644 --- a/ext/metadata/metadatamuxpng.c +++ b/ext/metadata/metadatamuxpng.c @@ -50,14 +50,6 @@ metadatamux_png_reading (PngMuxData * png_data, guint8 ** buf, guint32 * bufsize, const guint32 offset, const guint8 * step_buf, guint8 ** next_start, guint32 * next_size); -static int -metadatamux_png_xmp (PngMuxData * png_data, guint8 ** buf, - guint32 * bufsize, guint8 ** next_start, guint32 * next_size); - -static int -metadatamux_png_jump (PngMuxData * png_data, guint8 ** buf, - guint32 * bufsize, guint8 ** next_start, guint32 * next_size); - #define READ(buf, size) ( (size)--, *((buf)++) ) void @@ -78,14 +70,11 @@ metadatamux_png_init (PngMuxData * png_data, GstAdapter ** exif_adpt, png_data->strip_chunks = strip_chunks; png_data->inject_chunks = inject_chunks; - metadataparse_xmp_init (); } void metadatamux_png_dispose (PngMuxData * png_data) { - metadataparse_xmp_dispose (); - png_data->xmp_adapter = NULL; } @@ -139,16 +128,6 @@ metadatamux_png_parse (PngMuxData * png_data, guint8 * buf, metadatamux_png_reading (png_data, &buf, bufsize, offset, step_buf, next_start, next_size); break; - case PNG_MUX_JUMPING: - ret = - metadatamux_png_jump (png_data, &buf, bufsize, next_start, - next_size); - break; - case PNG_MUX_XMP: - ret = - metadatamux_png_xmp (png_data, &buf, bufsize, next_start, - next_size); - break; case PNG_MUX_DONE: goto done; break; @@ -175,6 +154,7 @@ metadatamux_png_reading (PngMuxData * png_data, guint8 ** buf, int ret = -1; guint8 mark[4]; guint32 chunk_size = 0; + MetadataChunk chunk; static const char XmpHeader[] = "XML:com.adobe.xmp"; @@ -196,45 +176,22 @@ metadatamux_png_reading (PngMuxData * png_data, guint8 ** buf, mark[2] = READ (*buf, *bufsize); mark[3] = READ (*buf, *bufsize); - if (mark[0] == 'I' && mark[1] == 'E' && mark[2] == 'N' && mark[3] == 'D') { - ret = 0; - png_data->state = PNG_MUX_DONE; + if (!(mark[0] == 'I' && mark[1] == 'H' && mark[2] == 'D' && mark[3] == 'R')) { + ret = -1; + png_data->state = PNG_MUX_NULL; goto done; } - if (mark[0] == 'i' && mark[1] == 'T' && mark[2] == 'X' && mark[3] == 't') { - if (chunk_size >= 22) { /* "XML:com.adobe.xmp" plus some flags */ - if (*bufsize < 22) { - *next_size = (*buf - *next_start) + 22; - ret = 1; - goto done; - } - - if (0 == memcmp (XmpHeader, *buf, 18)) { - MetadataChunk chunk; - - memset (&chunk, 0x00, sizeof (MetadataChunk)); - chunk.offset_orig = (*buf - step_buf) + offset - 8; /* maker + size */ - chunk.size = chunk_size + 12; /* chunk size plus app marker plus crc */ - - metadata_chunk_array_append_sorted (png_data->strip_chunks, &chunk); - - /* if adapter has been provided, prepare to hold chunk */ - if (png_data->xmp_adapter) { - *buf += 22; /* jump "XML:com.adobe.xmp" plus some flags */ - *bufsize -= 22; - png_data->read = chunk_size - 22; /* four CRC bytes at the end will be jumped after */ - png_data->state = PNG_MUX_XMP; - ret = 0; - goto done; - } - } - } - } + /* always inject after first chunk (IHDR) */ + + memset (&chunk, 0x00, sizeof (MetadataChunk)); + /* 8(header) + 4(size) +4(id) + chunksize + 4(crc) */ + chunk.offset_orig = chunk_size + 20; + chunk.type = MD_CHUNK_XMP; - /* just set jump sise */ - png_data->read = chunk_size + 4; /* four CRC bytes at the end */ - png_data->state = PNG_MUX_JUMPING; + metadata_chunk_array_append_sorted (png_data->inject_chunks, &chunk); + + png_data->state = PNG_MUX_DONE; ret = 0; done: @@ -243,31 +200,3 @@ done: } - -static int -metadatamux_png_jump (PngMuxData * png_data, guint8 ** buf, - guint32 * bufsize, guint8 ** next_start, guint32 * next_size) -{ - png_data->state = PNG_MUX_READING; - return metadataparse_util_jump_chunk (&png_data->read, buf, - bufsize, next_start, next_size); -} - -static int -metadatamux_png_xmp (PngMuxData * png_data, guint8 ** buf, - guint32 * bufsize, guint8 ** next_start, guint32 * next_size) -{ - int ret; - - ret = metadataparse_util_hold_chunk (&png_data->read, buf, - bufsize, next_start, next_size, png_data->xmp_adapter); - if (ret == 0) { - /* jump four CRC bytes at the end of chunk */ - png_data->read = 4; - png_data->state = PNG_MUX_JUMPING; - /* if there is a second XMP chunk in the file it will be jumped */ - png_data->xmp_adapter = NULL; - } - return ret; - -} diff --git a/ext/metadata/metadataparsejpeg.c b/ext/metadata/metadataparsejpeg.c index 1a129109..fb024150 100644 --- a/ext/metadata/metadataparsejpeg.c +++ b/ext/metadata/metadataparsejpeg.c @@ -91,14 +91,11 @@ metadataparse_jpeg_init (JpegParseData * jpeg_data, GstAdapter ** exif_adpt, jpeg_data->strip_chunks = strip_chunks; jpeg_data->inject_chunks = inject_chunks; - metadataparse_xmp_init (); } void metadataparse_jpeg_dispose (JpegParseData * jpeg_data) { - metadataparse_xmp_dispose (); - jpeg_data->exif_adapter = NULL; jpeg_data->iptc_adapter = NULL; jpeg_data->xmp_adapter = NULL; diff --git a/ext/metadata/metadataparsepng.c b/ext/metadata/metadataparsepng.c index d0cfa250..be5bb85b 100644 --- a/ext/metadata/metadataparsepng.c +++ b/ext/metadata/metadataparsepng.c @@ -78,14 +78,11 @@ metadataparse_png_init (PngParseData * png_data, GstAdapter ** exif_adpt, png_data->strip_chunks = strip_chunks; png_data->inject_chunks = inject_chunks; - metadataparse_xmp_init (); } void metadataparse_png_dispose (PngParseData * png_data) { - metadataparse_xmp_dispose (); - png_data->xmp_adapter = NULL; } @@ -213,6 +210,7 @@ metadataparse_png_reading (PngParseData * png_data, guint8 ** buf, memset (&chunk, 0x00, sizeof (MetadataChunk)); chunk.offset_orig = (*buf - step_buf) + offset - 8; /* maker + size */ chunk.size = chunk_size + 12; /* chunk size plus app marker plus crc */ + chunk.type = MD_CHUNK_XMP; metadata_chunk_array_append_sorted (png_data->strip_chunks, &chunk); diff --git a/ext/metadata/metadataxmp.c b/ext/metadata/metadataxmp.c index b417a935..f153ed25 100644 --- a/ext/metadata/metadataxmp.c +++ b/ext/metadata/metadataxmp.c @@ -75,7 +75,7 @@ metadataparse_xmp_dispose (void) } void -metadatamux_xmp_create_chunk_from_tag_list (GstAdapter ** adapter, +metadatamux_xmp_create_chunk_from_tag_list (guint8 ** buf, guint32 * size, GstTagList * taglist) { /* do nothing */ @@ -247,16 +247,29 @@ metadataparse_xmp_iter (XmpPtr xmp, XmpIteratorPtr iter) } void -metadatamux_xmp_create_chunk_from_tag_list (GstAdapter ** adapter, +metadatamux_xmp_create_chunk_from_tag_list (guint8 ** buf, guint32 * size, GstTagList * taglist) { - if (adapter == NULL) - goto done; - - if (*adapter) - g_object_unref (*adapter); + GstBuffer *xmp_chunk = NULL; + const GValue *val = NULL; - *adapter = gst_adapter_new (); + if (!(buf && size)) + goto done; + if (*buf) { + g_free (*buf); + *buf = NULL; + } + *size = 0; + + val = gst_tag_list_get_value_index (taglist, GST_TAG_XMP, 0); + if (val) { + xmp_chunk = gst_value_get_buffer (val); + if (xmp_chunk) { + *size = GST_BUFFER_SIZE (xmp_chunk); + *buf = g_new (guint8, *size); + memcpy (*buf, GST_BUFFER_DATA (xmp_chunk), *size); + } + } done: diff --git a/ext/metadata/metadataxmp.h b/ext/metadata/metadataxmp.h index f7454c5d..6cb635d3 100644 --- a/ext/metadata/metadataxmp.h +++ b/ext/metadata/metadataxmp.h @@ -59,7 +59,7 @@ extern gboolean metadataparse_xmp_init (void); extern void metadataparse_xmp_dispose (void); extern void -metadatamux_xmp_create_chunk_from_tag_list (GstAdapter ** adapter, +metadatamux_xmp_create_chunk_from_tag_list (guint8 ** buf, guint32 *size, GstTagList * taglist); G_END_DECLS -- cgit v1.2.1