mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2025-04-26 06:54:49 +00:00
tag: fix writing of Exif tag payloads <= 4 bytes
When the payload for an Exif tag is less than or equal to 4 bytes, the data is simply put into the offset field. Fix writing these kinds of payloads on big endian systems (and possibly also on little endian systems). The caller will have already formatted the bytes in memory according to the writer's endianness, so just write out the bytes as they are in this case. Fixes tags unit test on big endian systems.
This commit is contained in:
parent
e3c78ff661
commit
dfa23662e1
2 changed files with 22 additions and 16 deletions
|
@ -612,7 +612,7 @@ gst_tag_list_has_ifd_tags (const GstTagList * taglist,
|
||||||
static void
|
static void
|
||||||
gst_exif_writer_write_tag_header (GstExifWriter * writer,
|
gst_exif_writer_write_tag_header (GstExifWriter * writer,
|
||||||
guint16 exif_tag, guint16 exif_type, guint32 count, guint32 offset,
|
guint16 exif_tag, guint16 exif_type, guint32 count, guint32 offset,
|
||||||
gboolean is_data)
|
const guint32 * offset_data)
|
||||||
{
|
{
|
||||||
GST_DEBUG ("Writing tag entry: id %x, type %u, count %u, offset %u",
|
GST_DEBUG ("Writing tag entry: id %x, type %u, count %u, offset %u",
|
||||||
exif_tag, exif_type, count, offset);
|
exif_tag, exif_type, count, offset);
|
||||||
|
@ -621,13 +621,17 @@ gst_exif_writer_write_tag_header (GstExifWriter * writer,
|
||||||
gst_byte_writer_put_uint16_le (&writer->tagwriter, exif_tag);
|
gst_byte_writer_put_uint16_le (&writer->tagwriter, exif_tag);
|
||||||
gst_byte_writer_put_uint16_le (&writer->tagwriter, exif_type);
|
gst_byte_writer_put_uint16_le (&writer->tagwriter, exif_type);
|
||||||
gst_byte_writer_put_uint32_le (&writer->tagwriter, count);
|
gst_byte_writer_put_uint32_le (&writer->tagwriter, count);
|
||||||
gst_byte_writer_put_uint32_le (&writer->tagwriter, offset);
|
if (offset_data != NULL) {
|
||||||
|
gst_byte_writer_put_data (&writer->tagwriter, (guint8 *) offset_data, 4);
|
||||||
|
} else {
|
||||||
|
gst_byte_writer_put_uint32_le (&writer->tagwriter, offset);
|
||||||
|
}
|
||||||
} else if (writer->byte_order == G_BIG_ENDIAN) {
|
} else if (writer->byte_order == G_BIG_ENDIAN) {
|
||||||
gst_byte_writer_put_uint16_be (&writer->tagwriter, exif_tag);
|
gst_byte_writer_put_uint16_be (&writer->tagwriter, exif_tag);
|
||||||
gst_byte_writer_put_uint16_be (&writer->tagwriter, exif_type);
|
gst_byte_writer_put_uint16_be (&writer->tagwriter, exif_type);
|
||||||
gst_byte_writer_put_uint32_be (&writer->tagwriter, count);
|
gst_byte_writer_put_uint32_be (&writer->tagwriter, count);
|
||||||
if (is_data) {
|
if (offset_data != NULL) {
|
||||||
gst_byte_writer_put_uint32_le (&writer->tagwriter, offset);
|
gst_byte_writer_put_data (&writer->tagwriter, (guint8 *) offset_data, 4);
|
||||||
} else {
|
} else {
|
||||||
gst_byte_writer_put_uint32_be (&writer->tagwriter, offset);
|
gst_byte_writer_put_uint32_be (&writer->tagwriter, offset);
|
||||||
}
|
}
|
||||||
|
@ -671,7 +675,7 @@ gst_exif_writer_write_rational_tag (GstExifWriter * writer,
|
||||||
guint32 offset = gst_byte_writer_get_size (&writer->datawriter);
|
guint32 offset = gst_byte_writer_get_size (&writer->datawriter);
|
||||||
|
|
||||||
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_RATIONAL,
|
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_RATIONAL,
|
||||||
1, offset, FALSE);
|
1, offset, NULL);
|
||||||
|
|
||||||
gst_exif_writer_write_rational_data (writer, frac_n, frac_d);
|
gst_exif_writer_write_rational_data (writer, frac_n, frac_d);
|
||||||
}
|
}
|
||||||
|
@ -683,7 +687,7 @@ gst_exif_writer_write_signed_rational_tag (GstExifWriter * writer,
|
||||||
guint32 offset = gst_byte_writer_get_size (&writer->datawriter);
|
guint32 offset = gst_byte_writer_get_size (&writer->datawriter);
|
||||||
|
|
||||||
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_SRATIONAL,
|
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_SRATIONAL,
|
||||||
1, offset, FALSE);
|
1, offset, NULL);
|
||||||
|
|
||||||
gst_exif_writer_write_signed_rational_data (writer, frac_n, frac_d);
|
gst_exif_writer_write_signed_rational_data (writer, frac_n, frac_d);
|
||||||
}
|
}
|
||||||
|
@ -720,7 +724,7 @@ gst_exif_writer_write_byte_tag (GstExifWriter * writer, guint16 tag,
|
||||||
|
|
||||||
GST_WRITE_UINT8 ((guint8 *) & offset, value);
|
GST_WRITE_UINT8 ((guint8 *) & offset, value);
|
||||||
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_BYTE,
|
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_BYTE,
|
||||||
1, offset, TRUE);
|
1, offset, &offset);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
|
@ -736,7 +740,7 @@ gst_exif_writer_write_short_tag (GstExifWriter * writer, guint16 tag,
|
||||||
}
|
}
|
||||||
|
|
||||||
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_SHORT,
|
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_SHORT,
|
||||||
1, offset, TRUE);
|
1, offset, &offset);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
|
@ -751,7 +755,7 @@ gst_exif_writer_write_long_tag (GstExifWriter * writer, guint16 tag,
|
||||||
}
|
}
|
||||||
|
|
||||||
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_LONG,
|
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_LONG,
|
||||||
1, offset, TRUE);
|
1, offset, &offset);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -766,13 +770,13 @@ write_exif_undefined_tag (GstExifWriter * writer, guint16 tag,
|
||||||
* resulting tag headers offset and the base offset */
|
* resulting tag headers offset and the base offset */
|
||||||
offset = gst_byte_writer_get_size (&writer->datawriter);
|
offset = gst_byte_writer_get_size (&writer->datawriter);
|
||||||
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_UNDEFINED,
|
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_UNDEFINED,
|
||||||
size, offset, FALSE);
|
size, offset, NULL);
|
||||||
gst_byte_writer_put_data (&writer->datawriter, data, size);
|
gst_byte_writer_put_data (&writer->datawriter, data, size);
|
||||||
} else {
|
} else {
|
||||||
/* small enough to go in the offset */
|
/* small enough to go in the offset */
|
||||||
memcpy ((guint8 *) & offset, data, size);
|
memcpy ((guint8 *) & offset, data, size);
|
||||||
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_UNDEFINED,
|
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_UNDEFINED,
|
||||||
size, offset, TRUE);
|
size, offset, &offset);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -802,13 +806,13 @@ write_exif_ascii_tag (GstExifWriter * writer, guint16 tag, const gchar * str)
|
||||||
* resulting tag headers offset and the base offset */
|
* resulting tag headers offset and the base offset */
|
||||||
offset = gst_byte_writer_get_size (&writer->datawriter);
|
offset = gst_byte_writer_get_size (&writer->datawriter);
|
||||||
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_ASCII,
|
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_ASCII,
|
||||||
ascii_size, offset, FALSE);
|
ascii_size, offset, NULL);
|
||||||
gst_byte_writer_put_string (&writer->datawriter, ascii_str);
|
gst_byte_writer_put_string (&writer->datawriter, ascii_str);
|
||||||
} else {
|
} else {
|
||||||
/* small enough to go in the offset */
|
/* small enough to go in the offset */
|
||||||
memcpy ((guint8 *) & offset, ascii_str, ascii_size);
|
memcpy ((guint8 *) & offset, ascii_str, ascii_size);
|
||||||
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_ASCII,
|
gst_exif_writer_write_tag_header (writer, tag, EXIF_TYPE_ASCII,
|
||||||
ascii_size, offset, TRUE);
|
ascii_size, offset, &offset);
|
||||||
}
|
}
|
||||||
|
|
||||||
g_free (ascii_str);
|
g_free (ascii_str);
|
||||||
|
@ -1435,7 +1439,7 @@ parse_exif_rational_tag (GstExifReader * exif_reader,
|
||||||
}
|
}
|
||||||
|
|
||||||
static GstBuffer *
|
static GstBuffer *
|
||||||
write_exif_ifd (const GstTagList * taglist, gboolean byte_order,
|
write_exif_ifd (const GstTagList * taglist, guint byte_order,
|
||||||
guint32 base_offset, const GstExifTagMatch * tag_map)
|
guint32 base_offset, const GstExifTagMatch * tag_map)
|
||||||
{
|
{
|
||||||
GstExifWriter writer;
|
GstExifWriter writer;
|
||||||
|
@ -1492,7 +1496,7 @@ write_exif_ifd (const GstTagList * taglist, gboolean byte_order,
|
||||||
GST_DEBUG ("Adding inner ifd: %x", tag_map[i].exif_tag);
|
GST_DEBUG ("Adding inner ifd: %x", tag_map[i].exif_tag);
|
||||||
gst_exif_writer_write_tag_header (&writer, tag_map[i].exif_tag,
|
gst_exif_writer_write_tag_header (&writer, tag_map[i].exif_tag,
|
||||||
EXIF_TYPE_LONG, 1,
|
EXIF_TYPE_LONG, 1,
|
||||||
gst_byte_writer_get_size (&writer.datawriter), FALSE);
|
gst_byte_writer_get_size (&writer.datawriter), NULL);
|
||||||
gst_byte_writer_put_data (&writer.datawriter,
|
gst_byte_writer_put_data (&writer.datawriter,
|
||||||
GST_BUFFER_DATA (inner_ifd), GST_BUFFER_SIZE (inner_ifd));
|
GST_BUFFER_DATA (inner_ifd), GST_BUFFER_SIZE (inner_ifd));
|
||||||
gst_buffer_unref (inner_ifd);
|
gst_buffer_unref (inner_ifd);
|
||||||
|
@ -1939,7 +1943,7 @@ serialize_geo_coordinate (GstExifWriter * writer, const GstTagList * taglist,
|
||||||
|
|
||||||
offset = gst_byte_writer_get_size (&writer->datawriter);
|
offset = gst_byte_writer_get_size (&writer->datawriter);
|
||||||
gst_exif_writer_write_tag_header (writer, exiftag->exif_tag,
|
gst_exif_writer_write_tag_header (writer, exiftag->exif_tag,
|
||||||
EXIF_TYPE_RATIONAL, 3, offset, FALSE);
|
EXIF_TYPE_RATIONAL, 3, offset, NULL);
|
||||||
gst_exif_writer_write_rational_data (writer, degrees, 1);
|
gst_exif_writer_write_rational_data (writer, degrees, 1);
|
||||||
gst_exif_writer_write_rational_data (writer, minutes, 1);
|
gst_exif_writer_write_rational_data (writer, minutes, 1);
|
||||||
gst_exif_writer_write_rational_data (writer, seconds, 1);
|
gst_exif_writer_write_rational_data (writer, seconds, 1);
|
||||||
|
|
|
@ -1392,6 +1392,7 @@ do_exif_tag_serialization_deserialization (GstTagList * taglist)
|
||||||
|
|
||||||
/* LE */
|
/* LE */
|
||||||
buf = gst_tag_list_to_exif_buffer (taglist, G_LITTLE_ENDIAN, 0);
|
buf = gst_tag_list_to_exif_buffer (taglist, G_LITTLE_ENDIAN, 0);
|
||||||
|
GST_MEMDUMP ("Exif tag", GST_BUFFER_DATA (buf), GST_BUFFER_SIZE (buf));
|
||||||
taglist2 = gst_tag_list_from_exif_buffer (buf, G_LITTLE_ENDIAN, 0);
|
taglist2 = gst_tag_list_from_exif_buffer (buf, G_LITTLE_ENDIAN, 0);
|
||||||
gst_buffer_unref (buf);
|
gst_buffer_unref (buf);
|
||||||
|
|
||||||
|
@ -1400,6 +1401,7 @@ do_exif_tag_serialization_deserialization (GstTagList * taglist)
|
||||||
|
|
||||||
/* BE */
|
/* BE */
|
||||||
buf = gst_tag_list_to_exif_buffer (taglist, G_BIG_ENDIAN, 0);
|
buf = gst_tag_list_to_exif_buffer (taglist, G_BIG_ENDIAN, 0);
|
||||||
|
GST_MEMDUMP ("Exif tag", GST_BUFFER_DATA (buf), GST_BUFFER_SIZE (buf));
|
||||||
taglist2 = gst_tag_list_from_exif_buffer (buf, G_BIG_ENDIAN, 0);
|
taglist2 = gst_tag_list_from_exif_buffer (buf, G_BIG_ENDIAN, 0);
|
||||||
gst_buffer_unref (buf);
|
gst_buffer_unref (buf);
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue