From a6966f3927170103d326c205171ab7005355a450 Mon Sep 17 00:00:00 2001 From: Anas Nashif Date: Thu, 20 Jun 2013 09:10:13 -0400 Subject: [PATCH] add samsung device support --- libexif/Makefile.am | 12 +- libexif/exif-data.c | 214 +++++++++++- libexif/exif-data.h | 69 ++++ libexif/exif-entry.c | 4 + libexif/libexif.sym | 14 + libexif/samsung/Makefile-files | 7 + libexif/samsung/exif-mnote-data-samsung.c | 347 +++++++++++++++++++ libexif/samsung/exif-mnote-data-samsung.h | 51 +++ libexif/samsung/mnote-samsung-entry.c | 549 ++++++++++++++++++++++++++++++ libexif/samsung/mnote-samsung-entry.h | 52 +++ libexif/samsung/mnote-samsung-tag.c | 102 ++++++ libexif/samsung/mnote-samsung-tag.h | 84 +++++ packaging/libexif.changes | 3 + packaging/libexif.spec | 6 +- 14 files changed, 1506 insertions(+), 8 deletions(-) mode change 100644 => 100755 libexif/exif-data.c create mode 100644 libexif/samsung/Makefile-files create mode 100755 libexif/samsung/exif-mnote-data-samsung.c create mode 100755 libexif/samsung/exif-mnote-data-samsung.h create mode 100644 libexif/samsung/mnote-samsung-entry.c create mode 100644 libexif/samsung/mnote-samsung-entry.h create mode 100644 libexif/samsung/mnote-samsung-tag.c create mode 100644 libexif/samsung/mnote-samsung-tag.h diff --git a/libexif/Makefile.am b/libexif/Makefile.am index dde00ac..7d79d1f 100644 --- a/libexif/Makefile.am +++ b/libexif/Makefile.am @@ -6,6 +6,7 @@ include canon/Makefile-files include fuji/Makefile-files include olympus/Makefile-files include pentax/Makefile-files +include samsung/Makefile-files # The -no-undefined makes it possible to build DLLs for Windows, # or shared libraries for Tru64 or AIX (according to the autobook @@ -35,15 +36,20 @@ libexif_la_DEPENDENCIES = \ libmnote-canon.la \ libmnote-fuji.la \ libmnote-olympus.la \ - libmnote-pentax.la + libmnote-pentax.la \ + libmnote-samsung.la libexif_la_LIBADD = \ $(LTLIBINTL) \ libmnote-canon.la \ libmnote-fuji.la \ libmnote-olympus.la \ - libmnote-pentax.la + libmnote-pentax.la \ + libmnote-samsung.la libexifincludedir = $(includedir)/libexif +samsungincludedir = $(includedir)/libexif/samsung +samsunginclude_HEADERS = samsung/mnote-samsung-tag.h + libexifinclude_HEADERS = \ exif-byte-order.h \ exif-content.h \ @@ -58,7 +64,7 @@ libexifinclude_HEADERS = \ exif-mnote-data.h \ exif-tag.h \ exif-utils.h \ - _stdint.h + _stdint.h EXTRA_DIST += exif-system.h exif.h diff --git a/libexif/exif-data.c b/libexif/exif-data.c old mode 100644 new mode 100755 index 67df4db..f06ed65 --- a/libexif/exif-data.c +++ b/libexif/exif-data.c @@ -34,6 +34,7 @@ #include #include #include +#include #include #include @@ -88,6 +89,12 @@ exif_data_get_mnote_data (ExifData *d) return (d && d->priv) ? d->priv->md : NULL; } +ExifByteOrder +exif_data_get_data_order (ExifData *d) +{ + return (d && d->priv) ? d->priv->order : -1; +} + ExifData * exif_data_new (void) { @@ -722,7 +729,8 @@ typedef enum { EXIF_DATA_TYPE_MAKER_NOTE_PENTAX = 3, EXIF_DATA_TYPE_MAKER_NOTE_NIKON = 4, EXIF_DATA_TYPE_MAKER_NOTE_CASIO = 5, - EXIF_DATA_TYPE_MAKER_NOTE_FUJI = 6 + EXIF_DATA_TYPE_MAKER_NOTE_FUJI = 6, + EXIF_DATA_TYPE_MAKER_NOTE_SAMSUNG = 7 } ExifDataTypeMakerNote; /*! If MakerNote is recognized, load it. @@ -759,9 +767,12 @@ interpret_maker_note(ExifData *data, const unsigned char *d, unsigned int ds) } else if ((mnoteid = exif_mnote_data_pentax_identify (data, e)) != 0) { exif_log (data->priv->log, EXIF_LOG_CODE_DEBUG, "ExifData", "Pentax MakerNote variant type %d", mnoteid); - data->priv->md = exif_mnote_data_pentax_new (data->priv->mem); + data->priv->md = exif_mnote_data_pentax_new (data->priv->mem); + } else if ((mnoteid = exif_mnote_data_samsung_identify (data, e)) != 0) { + exif_log (data->priv->log, EXIF_LOG_CODE_DEBUG, + "ExifData", "Samsung MakerNote variant type %d", mnoteid); + data->priv->md = exif_mnote_data_samsung_new (data->priv->mem); } - /* * If we are able to interpret the maker note, do so. */ @@ -1274,3 +1285,200 @@ exif_data_get_data_type (ExifData *d) { return (d && d->priv) ? d->priv->data_type : EXIF_DATA_TYPE_UNKNOWN; } + +/* Used for making maker note data structure from external sources */ +int +exif_data_mnote_data_new(ExifData *d, Manufacturer maker, ExifDataOption o) +{ + ExifMnoteData *md; + ExifMem *mem; + + if(!d) return 0; + + md = d->priv->md; + mem = d->priv->mem; + + switch(maker){ + case MAKER_CANON: + md = exif_mnote_data_canon_new(mem, o); + break; + case MAKER_FUJI: + md = exif_mnote_data_fuji_new(mem); + break; + case MAKER_OLYMPUS: + case MAKER_NIKON: + md = exif_mnote_data_olympus_new(mem); + break; + case MAKER_PENTAX: + case MAKER_CASIO: + md = exif_mnote_data_pentax_new(mem); + break; + case MAKER_SAMSUNG: + md = exif_mnote_data_samsung_new(mem); + break; + default: + break; + } + if(!md) + return 0; + else{ + d->priv->md = md; + return 1; + } +} + +int +exif_data_mnote_set_mem_for_adding_entry(ExifMnoteData *md, Manufacturer maker) +{ + ExifMem *mem; + unsigned int count; + ExifMnoteDataSamsung *mds; + + if(!md) return 0; + + mem = md->mem; + + switch(maker){ + case MAKER_CANON: + break; + case MAKER_FUJI: + break; + case MAKER_OLYMPUS: + case MAKER_NIKON: + break; + case MAKER_PENTAX: + case MAKER_CASIO: + break; + case MAKER_SAMSUNG: + mds = (ExifMnoteDataSamsung *) md; + count = ++(mds->count); + if(count == 1) { + mds->entries = exif_mem_alloc(mem, sizeof(MnoteSamsungEntry) * count); + if(!mds->entries) { + EXIF_LOG_NO_MEMORY(md->log, "ExifMnoteSamsung", count); + mds->count--; + return 0; + } + } + else { + MnoteSamsungEntry **e; + e = exif_mem_realloc(mem, mds->entries, sizeof(MnoteSamsungEntry) * count); + if(!e) { + EXIF_LOG_NO_MEMORY(md->log, "ExifMnoteSamsung", count); + mds->count--; + return 0; + } + mds->entries = e; + } + mds->entries[count-1].format = 0; + break; + default: + return 0; + } + return 1; +} + +int +exif_data_mnote_set_add_entry (ExifMnoteData* md, Manufacturer maker, int tag, ExifFormat fmt, int components, int id) +{ + int count; + ExifMnoteDataSamsung *mds; + + if(!md) return 0; + + switch(maker){ + case MAKER_CANON: + break; + case MAKER_FUJI: + break; + case MAKER_OLYMPUS: + case MAKER_NIKON: + break; + case MAKER_PENTAX: + case MAKER_CASIO: + break; + case MAKER_SAMSUNG: + mds = (ExifMnoteDataSamsung *) md; + count = mds->count; + mds->entries[count-1].tag = tag; + mds->entries[count-1].format = fmt; + mds->entries[count-1].components = components; + mds->entries[count-1].size = exif_format_get_size(fmt*components); + mds->entries[count-1].data = exif_mem_alloc(md->mem, mds->entries[count-1].size); + mnote_samsung_entry_set_value_by_index(&mds->entries[count-1], id); + break; + default: + return 0; + } + return 1; +} + +int +exif_data_mnote_set_add_entry_subtag(ExifMnoteData* md, Manufacturer maker, int tag, ExifFormat fmt, int components, int subtag1, int id1, int subtag2, int id2, int val) +{ + int count; + ExifMnoteDataSamsung *mds; + + if(!md) return 0; + + switch(maker){ + case MAKER_CANON: + break; + case MAKER_FUJI: + break; + case MAKER_OLYMPUS: + case MAKER_NIKON: + break; + case MAKER_PENTAX: + case MAKER_CASIO: + break; + case MAKER_SAMSUNG: + mds = (ExifMnoteDataSamsung *) md; + count = mds->count; + mds->entries[count-1].tag = tag; + mds->entries[count-1].format = fmt; + mds->entries[count-1].components = components; + mds->entries[count-1].size = exif_format_get_size(fmt*components); + mds->entries[count-1].data = exif_mem_alloc(md->mem, mds->entries[count-1].size); + mnote_samsung_entry_set_value_by_subtag(&mds->entries[count-1], subtag1, id1, subtag2, id2, val); + break; + default: + return 0; + } + return 1; +} + +int +exif_data_mnote_set_add_entry_string(ExifMnoteData* md, Manufacturer maker, int tag, ExifFormat fmt, int components, const char* string) +{ + int count; + ExifMnoteDataSamsung *mds; + + if(!md) return 0; + + switch(maker){ + case MAKER_CANON: + break; + case MAKER_FUJI: + break; + case MAKER_OLYMPUS: + case MAKER_NIKON: + break; + case MAKER_PENTAX: + case MAKER_CASIO: + break; + case MAKER_SAMSUNG: + mds = (ExifMnoteDataSamsung *) md; + count = mds->count; + mds->entries[count-1].tag = tag; + mds->entries[count-1].format = fmt; + mds->entries[count-1].components = components; + mds->entries[count-1].size = exif_format_get_size(fmt*components); + mds->entries[count-1].data = exif_mem_alloc(md->mem, mds->entries[count-1].size); + mnote_samsung_entry_set_value_by_string(&mds->entries[count-1], string, components); + break; + default: + return 0; + } + return 1; +} diff --git a/libexif/exif-data.h b/libexif/exif-data.h index eeee782..d45fbab 100644 --- a/libexif/exif-data.h +++ b/libexif/exif-data.h @@ -42,6 +42,16 @@ typedef struct _ExifDataPrivate ExifDataPrivate; #include #include +typedef enum{ + MAKER_CANON = 1, + MAKER_OLYMPUS = 2, + MAKER_PENTAX = 3, + MAKER_NIKON = 4, + MAKER_CASIO = 5, + MAKER_FUJI = 6, + MAKER_SAMSUNG = 7 +}Manufacturer; + /*! Represents the entire EXIF data found in an image */ struct _ExifData { @@ -149,6 +159,8 @@ void exif_data_set_byte_order (ExifData *data, ExifByteOrder order); */ ExifMnoteData *exif_data_get_mnote_data (ExifData *d); +ExifByteOrder exif_data_get_data_order (ExifData *d); + /*! Fix the EXIF data to bring it into specification. Call #exif_content_fix * on each IFD to fix existing entries, create any new entries that are * mandatory but do not yet exist, and remove any entries that are not @@ -238,6 +250,63 @@ void exif_data_dump (ExifData *data); */ void exif_data_log (ExifData *data, ExifLog *log); +/*! Create new mnote data and set up related function pointers for particular manufacturer. + * + * \param[in,out] d EXIF data + * \param[in] maker Manufacturer + * \param[in] o option + * \return 1 if normal, else 0 if abnormal + */ +int exif_data_mnote_data_new(ExifData *d, Manufacturer maker, ExifDataOption o); + +/*! Allocate makernote entries memory for particular manufacturer. + * + * \param[in,out] d EXIF Makernote data + * \param[in] maker Manufacturer + * \return 1 if normal, else 0 if abnormal + */ +int exif_data_mnote_set_mem_for_adding_entry(ExifMnoteData *md, Manufacturer maker); + +/*! Add a makernote entry for particular manufacturer. + * + * \param[in,out] d EXIF Makernote data + * \param[in] maker Manufacturer + * \param[in] tag Manufacturer specified makernote tag + * \param[in] fmt Exifformat + * \param[in] components The number of components + * \param[in] id Index + * \return 1 if normal, else 0 if abnormal + */ +int exif_data_mnote_set_add_entry(ExifMnoteData *md, Manufacturer maker, int tag, ExifFormat fmt, int components, int id); + +/*! Add a makernote entry using subtag information for particular manufacturer. + * + * \param[in,out] d EXIF Makernote data + * \param[in] maker Manufacturer + * \param[in] tag Manufacturer specified makernote tag + * \param[in] fmt Exifformat + * \param[in] components The number of components + * \param[in] subtag1 Manufacturer specified makernote subtag + * \param[in] id1 Index for subtag1 + * \param[in] subtag2 Manufacturer specified makernote subtag + * \param[in] id2 Indoex for subtag2 + * \param[in] val Integer value + * \return 1 if normal, else 0 if abnormal +*/ +int exif_data_mnote_set_add_entry_subtag(ExifMnoteData* md, Manufacturer maker, int tag, ExifFormat fmt, int components, int subtag1, int id1, int subtag2, int id2, int val); + +/*! Add a makernote entry using string information for particular manufacturer. + * + * \param[in,out] d EXIF Makernote data + * \param[in] maker Manufacturer + * \param[in] tag Manufacturer specified makernote tag + * \param[in] fmt Exifformat + * \param[in] components The number of components + * \param[in] string String value to be written + * \return 1 if normal, else 0 if abnormal + */ +int exif_data_mnote_set_add_entry_string(ExifMnoteData* md, Manufacturer maker, int tag, ExifFormat fmt, int components, const char* string); + /*! Return an #ExifEntry for the given tag if found in any IFD. * Each IFD is searched in turn and the first containing a tag with * this number is returned. diff --git a/libexif/exif-entry.c b/libexif/exif-entry.c index 54a90a2..ae91a7f 100644 --- a/libexif/exif-entry.c +++ b/libexif/exif-entry.c @@ -941,6 +941,10 @@ exif_entry_get_value (ExifEntry *e, char *val, unsigned int maxlen) } break; + case EXIF_TAG_MAKE: + strncpy (val, (char *) e->data, MIN (e->size, maxlen)); + break; + case EXIF_TAG_EXIF_VERSION: CF (e, EXIF_FORMAT_UNDEFINED, val, maxlen); CC (e, 4, val, maxlen); diff --git a/libexif/libexif.sym b/libexif/libexif.sym index f1d77cf..6ba78e1 100644 --- a/libexif/libexif.sym +++ b/libexif/libexif.sym @@ -21,6 +21,7 @@ exif_data_get_byte_order exif_data_get_data_type exif_data_get_log exif_data_get_mnote_data +exif_data_get_data_order exif_data_load_data exif_data_log exif_data_new @@ -36,6 +37,11 @@ exif_data_set_data_type exif_data_set_option exif_data_unref exif_data_unset_option +exif_data_mnote_data_new +exif_data_mnote_set_mem_for_adding_entry +exif_data_mnote_set_add_entry +exif_data_mnote_set_add_entry_subtag +exif_data_mnote_set_add_entry_string exif_entry_dump exif_entry_fix exif_entry_free @@ -92,6 +98,7 @@ exif_mnote_data_load exif_mnote_data_log exif_mnote_data_olympus_new exif_mnote_data_pentax_new +exif_mnote_data_samsung_new exif_mnote_data_ref exif_mnote_data_save exif_mnote_data_set_byte_order @@ -126,4 +133,11 @@ mnote_pentax_entry_get_value mnote_pentax_tag_get_description mnote_pentax_tag_get_name mnote_pentax_tag_get_title +mnote_samsung_entry_get_value +mnote_samsung_entry_set_value_by_index +mnote_samsung_entry_set_value_by_string +mnote_samsung_entry_set_value_by_subtag +mnote_samsung_tag_get_description +mnote_samsung_tag_get_name +mnote_samsung_tag_get_title exif_loader_get_buf diff --git a/libexif/samsung/Makefile-files b/libexif/samsung/Makefile-files new file mode 100644 index 0000000..f11aece --- /dev/null +++ b/libexif/samsung/Makefile-files @@ -0,0 +1,7 @@ +# -*- Makefile -*- +noinst_LTLIBRARIES += libmnote-samsung.la +libmnote_samsung_la_SOURCES = \ + samsung/mnote-samsung-entry.c samsung/mnote-samsung-entry.h \ + samsung/exif-mnote-data-samsung.c samsung/exif-mnote-data-samsung.h \ + samsung/mnote-samsung-tag.c samsung/mnote-samsung-tag.h +libmnote_samsung_la_LIBADD = $(LTLIBINTL) diff --git a/libexif/samsung/exif-mnote-data-samsung.c b/libexif/samsung/exif-mnote-data-samsung.c new file mode 100755 index 0000000..2524ae4 --- /dev/null +++ b/libexif/samsung/exif-mnote-data-samsung.c @@ -0,0 +1,347 @@ +/* + * libexif + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Sangchul Lee + * + * This library is free software; you can redistribute it and/or modify it under + * the terms of the GNU Lesser General Public License as published by the + * Free Software Foundation; either version 2.1 of the License, or (at your option) + * any later version. + * + * This library is distributed in the hope that it will be useful, but WITHOUT ANY + * WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this library; if not, write to the Free Software Foundation, Inc., 51 + * Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * + */ + + +#include "config.h" +#include "exif-mnote-data-samsung.h" + +#include +#include +#include + +#include +#include + +#define DEBUG + +static void exif_mnote_data_samsung_clear (ExifMnoteDataSamsung *mds) +{ + ExifMnoteData *md = (ExifMnoteData *) mds; + unsigned int i; + + if (!mds) return; + + if (mds->entries) { + for (i = 0; i < mds->count; i++) + if (mds->entries[i].data) { + exif_mem_free (md->mem, mds->entries[i].data); + mds->entries[i].data = NULL; + } + exif_mem_free (md->mem, mds->entries); + mds->entries = NULL; + mds->count = 0; + } +} + +static void exif_mnote_data_samsung_free (ExifMnoteData *md) +{ + if (!md) return; + + exif_mnote_data_samsung_clear ((ExifMnoteDataSamsung *) md); +} + +static char *exif_mnote_data_samsung_get_value (ExifMnoteData *md, unsigned int i, char *val, unsigned int maxlen) +{ + ExifMnoteDataSamsung *mds = (ExifMnoteDataSamsung *) md; + + if (!md || !val) return NULL; + if (i > mds->count -1) return NULL; + exif_log (md->log, EXIF_LOG_CODE_DEBUG, "ExifMnoteDataSamsung", + "Querying value for tag '%s'...", + mnote_samsung_tag_get_name (mds->entries[i].tag)); + return mnote_samsung_entry_get_value (&mds->entries[i], val, maxlen); +} + + +/** + * @brief save the MnoteData from md to buf + * + * @param md extract the data from this structure + * @param *buf write the mnoteData to this buffer (buffer will be allocated) + * @param buf_size the size of the buffer + */ +static void exif_mnote_data_samsung_save (ExifMnoteData *md, + unsigned char **buf, unsigned int *buf_size) +{ + ExifMnoteDataSamsung *mds = (ExifMnoteDataSamsung *) md; + size_t i, off, val_size, doff; + unsigned char *new_buf; + size_t new_buf_size; + + if (!mds || !buf || !buf_size) return; + + /* + * Allocate enough memory for all entries and the number of entries. + */ + *buf_size = 2 + mds->count * 12 + 4; + *buf = exif_mem_alloc (md->mem, *buf_size); + if (!*buf) { + EXIF_LOG_NO_MEMORY(md->log, "ExifMnoteDataSamsung", *buf_size); + return; + } + + /* Save the number of entries */ + exif_set_short(*buf, mds->order, (ExifShort) mds->count); + + /* Save entries */ + for (i = 0; i < mds->count; i++) { + off = 2 + i * 12; + + exif_set_short (*buf + off + 0, mds->order, (ExifShort) mds->entries[i].tag); + exif_set_short (*buf + off + 2, mds->order, (ExifShort) mds->entries[i].format); + exif_set_long (*buf + off + 4, mds->order, mds->entries[i].components); + off += 8; + val_size = exif_format_get_size (mds->entries[i].format) * mds->entries[i].components; + + if (val_size > 65536) { + /* Corrupt data: EXIF data size is limited to the + * maximum size of a JPEG segment (64 kb). + */ + continue; + } + if (val_size > 4) { + new_buf_size = *buf_size + val_size; + if(val_size & 1) + new_buf_size += 1; + + new_buf = exif_mem_realloc (md->mem, *buf, sizeof (char) * new_buf_size); + if (!new_buf) { + EXIF_LOG_NO_MEMORY(md->log, "ExifMnoteDataSamsung", new_buf_size); + return; + } + doff = *buf_size; + *buf = new_buf; + *buf_size = new_buf_size; + + if(val_size & 1) + *(*buf + *buf_size - 1) = '\0'; + + //exif_set_long (*buf + off, mds->order, mds->offset + doff); + exif_set_long (*buf + off, mds->order, doff); + } else + doff = off; + + /* Write the data. */ + if (mds->entries[i].data) { + memcpy (*buf + doff, mds->entries[i].data, val_size); + //fprintf(stdout, "in exif_mnote_data_samsung_save (write the data to buffer)\n"); + //fprintf(stdout, " mds->entries[%d].data size : %d \n",i, val_size ); + //fprintf(stdout, " mds->entries[%d].data : %s \n",i, mds->entries[i].data ); + //fprintf(stdout, " buff + %d : %s \n",doff, buf+doff ); + } else { + /* Most certainly damaged input file */ + memset (*buf + doff, 0, val_size); + } + } +} + +static void exif_mnote_data_samsung_load (ExifMnoteData *md, + const unsigned char *buf, unsigned int buf_size) +{ + ExifMnoteDataSamsung *mds = (ExifMnoteDataSamsung *) md; + ExifShort entry_count; + size_t i, tcount, off, datao; + size_t val_size; + + if (!mds || !buf || !buf_size) { + exif_log (md->log, EXIF_LOG_CODE_CORRUPT_DATA, + "ExifMnoteDataSamsung", "Short MakerNote"); + return; + } + datao = mds->offset; /* Start of interesting data */ + datao += 6; + + if ((datao + 2 < datao) || (datao + 2 < 2) || (datao + 2 > buf_size)) { + exif_log (md->log, EXIF_LOG_CODE_CORRUPT_DATA, + "ExifMnoteDataSamsung", "Short MakerNote"); + return; + } + + /* Read the number of Makernote Entries */ + entry_count = exif_get_short (buf + datao, mds->order); + + datao += 2; + + /* Remove any old entries */ + exif_mnote_data_samsung_clear (mds); + + /* Reserve enough space for all the possible MakerNote tags */ + mds->entries = exif_mem_alloc (md->mem, sizeof (MnoteSamsungEntry) * entry_count); + if (!mds->entries) { + EXIF_LOG_NO_MEMORY(md->log, "ExifMnoteSamsung", sizeof (MnoteSamsungEntry) * entry_count); + return; + } + + /* Parse all entries */ + tcount = 0; + + for (i = entry_count, off = datao; i; --i, off += 12) { + + if ((off + 12 < off) || (off + 12 < 12) || (off + 12 > buf_size)) { + exif_log (md->log, EXIF_LOG_CODE_CORRUPT_DATA, + "ExifMnoteSamsung", "Short MakerNote"); + break; + } + + mds->entries[tcount].tag = exif_get_short (buf + off, mds->order); + mds->entries[tcount].format = exif_get_short (buf + off + 2, mds->order); + mds->entries[tcount].components = exif_get_long (buf + off + 4, mds->order); + mds->entries[tcount].order = mds->order; + + exif_log (md->log, EXIF_LOG_CODE_DEBUG, "ExifMnoteSamsung","Loading entry 0x%x ('%s')...", mds->entries[tcount].tag, mnote_samsung_tag_get_name (mds->entries[tcount].tag)); + + val_size = exif_format_get_size (mds->entries[tcount].format) * mds->entries[tcount].components; + mds->entries[tcount].size = val_size; + + + if (val_size) { + size_t dataofs = off + 8; + if (val_size > 4) + dataofs = exif_get_long (buf + dataofs, mds->order) + datao - 2; // 2bytes for No. of IFD Entry field size + + if ((dataofs + val_size < dataofs) || (dataofs + val_size < val_size) || (dataofs + val_size > buf_size)) { + exif_log (md->log, EXIF_LOG_CODE_DEBUG, "ExifMnoteSamsung", "Tag data past end of buffer (%u > %u)", dataofs + val_size, buf_size); + continue; + } + + mds->entries[tcount].data = exif_mem_alloc (md->mem, val_size); + if (!mds->entries[tcount].data) { + EXIF_LOG_NO_MEMORY(md->log, "ExifMnoteSamsung", val_size); + continue; + } + memcpy (mds->entries[tcount].data, buf + dataofs, val_size); + + }else{ + exif_log (md->log, EXIF_LOG_CODE_CORRUPT_DATA, "ExifMnoteSamsung", "Invalid zero-length tag size"); + continue; + } + + /* Tag was successfully parsed */ + ++tcount; + } + /* Store the count of successfully parsed tags */ + mds->count = tcount; +} + +static unsigned int exif_mnote_data_samsung_count (ExifMnoteData *md) +{ + return md ? ((ExifMnoteDataSamsung *) md)->count : 0; +} + +static unsigned int exif_mnote_data_samsung_get_id (ExifMnoteData *md, unsigned int n) +{ + ExifMnoteDataSamsung *mds = (ExifMnoteDataSamsung *) md; + + if (!mds) return 0; + if (mds->count <= n) return 0; + return mds->entries[n].tag; +} + +static const char *exif_mnote_data_samsung_get_name (ExifMnoteData *md, unsigned int i) +{ + ExifMnoteDataSamsung *mds = (ExifMnoteDataSamsung *) md; + + if (!mds) return NULL; + if (i >= mds->count) return NULL; + return mnote_samsung_tag_get_name (mds->entries[i].tag); +} + +static const char * +exif_mnote_data_samsung_get_title (ExifMnoteData *note, unsigned int i) +{ + ExifMnoteDataSamsung *dc = (ExifMnoteDataSamsung *) note; + unsigned int m, s; + + if (!dc) return NULL; + exif_mnote_data_canon_get_tags (dc, i, &m, &s); + if (m >= dc->count) return NULL; + return mnote_samsung_tag_get_title_sub (dc->entries[m].tag, s, dc->options); +} + +static const char * +exif_mnote_data_samsung_get_description (ExifMnoteData *note, unsigned int i) +{ + ExifMnoteDataSamsung *dc = (ExifMnoteDataSamsung *) note; + unsigned int m; + + if (!dc) return NULL; + exif_mnote_data_canon_get_tags (dc, i, &m, NULL); + if (m >= dc->count) return NULL; + return mnote_samsung_tag_get_description (dc->entries[m].tag); +} + +int +exif_mnote_data_samsung_identify (const ExifData *ed, const ExifEntry *e) +{ + char value[8]; + ExifEntry *em = exif_data_get_entry (ed, EXIF_TAG_MAKE); + if (!em) + return 0; + return !strcmp (exif_entry_get_value (em, value, sizeof (value)), "samsung"); +} + +static void exif_mnote_data_samsung_set_byte_order (ExifMnoteData *md, ExifByteOrder o) +{ + ExifByteOrder o_orig; + ExifMnoteDataSamsung *mds = (ExifMnoteDataSamsung *) md; + unsigned int i; + + if (!mds) return; + + o_orig = mds->order; + mds->order = o; + for (i = 0; i < mds->count; i++) { + mds->entries[i].order = o; + exif_array_set_byte_order (mds->entries[i].format, mds->entries[i].data, mds->entries[i].components, o_orig, o); + } +} + +static void exif_mnote_data_samsung_set_offset (ExifMnoteData *md, unsigned int o) +{ + if (md) ((ExifMnoteDataSamsung *) md)->offset = o; +} + +ExifMnoteData *exif_mnote_data_samsung_new (ExifMem *mem) +{ + ExifMnoteData *md; + + if (!mem) return NULL; + + md = exif_mem_alloc (mem, sizeof (ExifMnoteDataSamsung)); + if (!md) return NULL; + + exif_mnote_data_construct (md, mem); + + /* Set up function pointers */ + md->methods.free = exif_mnote_data_samsung_free; + md->methods.set_byte_order = exif_mnote_data_samsung_set_byte_order; + md->methods.set_offset = exif_mnote_data_samsung_set_offset; + md->methods.load = exif_mnote_data_samsung_load; + md->methods.save = exif_mnote_data_samsung_save; + md->methods.count = exif_mnote_data_samsung_count; + md->methods.get_id = exif_mnote_data_samsung_get_id; + md->methods.get_name = exif_mnote_data_samsung_get_name; + md->methods.get_value = exif_mnote_data_samsung_get_value; + + return md; +} diff --git a/libexif/samsung/exif-mnote-data-samsung.h b/libexif/samsung/exif-mnote-data-samsung.h new file mode 100755 index 0000000..3626185 --- /dev/null +++ b/libexif/samsung/exif-mnote-data-samsung.h @@ -0,0 +1,51 @@ +/* + * libexif + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Sangchul Lee + * + * This library is free software; you can redistribute it and/or modify it under + * the terms of the GNU Lesser General Public License as published by the + * Free Software Foundation; either version 2.1 of the License, or (at your option) + * any later version. + * + * This library is distributed in the hope that it will be useful, but WITHOUT ANY + * WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this library; if not, write to the Free Software Foundation, Inc., 51 + * Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * + */ + +#ifndef __EXIF_MNOTE_DATA_SAMSUNG_H__ +#define __EXIF_MNOTE_DATA_SAMSUNG_H__ + +#include +#include +#include +#include +#include +#include + +typedef struct _ExifMnoteDataSamsung ExifMnoteDataSamsung; + +struct _ExifMnoteDataSamsung { + ExifMnoteData parent; + + MnoteSamsungEntry *entries; + unsigned int count; + + ExifByteOrder order; + unsigned int offset; + + ExifDataOption options; +}; + +int exif_mnote_data_samsung_identify (const ExifData *ed, const ExifEntry *e); +ExifMnoteData *exif_mnote_data_samsung_new (ExifMem *mem); + +#endif /* __EXIF_MNOTE_DATA_SAMSUNG_H__ */ diff --git a/libexif/samsung/mnote-samsung-entry.c b/libexif/samsung/mnote-samsung-entry.c new file mode 100644 index 0000000..1e17ae8 --- /dev/null +++ b/libexif/samsung/mnote-samsung-entry.c @@ -0,0 +1,549 @@ +/* + * libexif + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Sangchul Lee + * + * This library is free software; you can redistribute it and/or modify it under + * the terms of the GNU Lesser General Public License as published by the + * Free Software Foundation; either version 2.1 of the License, or (at your option) + * any later version. + * + * This library is distributed in the hope that it will be useful, but WITHOUT ANY + * WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this library; if not, write to the Free Software Foundation, Inc., 51 + * Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * + */ + +#include +#include "mnote-samsung-entry.h" + +#include +#include +#include + +#include +#include +#include +#include + +#define CF(format,target,v,maxlen) \ +{ \ + if (format != target) { \ + snprintf (v, maxlen, \ + _("Invalid format '%s', " \ + "expected '%s'."), \ + exif_format_get_name (format), \ + exif_format_get_name (target)); \ + break; \ + } \ +} + +#define CF2(format,target1,target2,v,maxlen) \ +{ \ + if ((format != target1) && (format != target2)) { \ + snprintf (v, maxlen, \ + _("Invalid format '%s', " \ + "expected '%s' or '%s'."), \ + exif_format_get_name (format), \ + exif_format_get_name (target1), \ + exif_format_get_name (target2)); \ + break; \ + } \ +} + +#define CC(number,target,v,maxlen) \ +{ \ + if (number != target) { \ + snprintf (v, maxlen, \ + _("Invalid number of components (%i, " \ + "expected %i)."), (int) number, (int) target); \ + break; \ + } \ +} + +#define CC2(number,t1,t2,v,maxlen) \ +{ \ + if ((number < t1) || (number > t2)) { \ + snprintf (v, maxlen, \ + _("Invalid number of components (%i, " \ + "expected %i or %i)."), (int) number, \ + (int) t1, (int) t2); \ + break; \ + } \ +} + +static const struct { + ExifTag tag; + ExifFormat fmt; + struct { + int index; + const char *string; + } elem[20]; +} items[] = { +#ifndef NO_VERBOSE_TAG_DATA + { MNOTE_SAMSUNG_TAG_MNOTE_VERSION, EXIF_FORMAT_UNDEFINED, + { {0x30313030, N_("MakerNote Version")}, + {0, NULL}}}, + { MNOTE_SAMSUNG_TAG_DEVICE_ID, EXIF_FORMAT_LONG, + { {0x00001000, N_("Compact")}, + {0x00002000, N_("DSLR")}, + {0x00003000, N_("Camcorder")}, + {0, NULL}}}, + { MNOTE_SAMSUNG_TAG_SERIAL_NUM, EXIF_FORMAT_ASCII, + { {0, NULL}}}, + { MNOTE_SAMSUNG_TAG_FAVOR_TAGGING, EXIF_FORMAT_LONG, + { {0x00000000, N_("Bad")}, + {0x00000001, N_("Good")}, + {0, NULL}}}, + { MNOTE_SAMSUNG_TAG_SRW_COMPRESS, EXIF_FORMAT_LONG, + { {0x00000000, N_("Uncompressed Mode")}, + {0x00000001, N_("Lossless Compression Mode (Type 1)")}, + {0x00000002, N_("Lossless Compression Mode (Type 2)")}, + {0, NULL}}}, + { MNOTE_SAMSUNG_TAG_COLOR_SPACE, EXIF_FORMAT_LONG, + { {0x00000001, N_("sRGB (Standard RGB)")}, + {0x0000FFFF, N_("Adobe RGB (Adobe RGB)")}, + {0, NULL}}}, + { MNOTE_SAMSUNG_TAG_SCENE_RESULT, EXIF_FORMAT_LONG, + { {0x00000000, N_("Smart")}, + {0x00000001, N_("Portrait")}, + {0x00000002, N_("Night")}, + {0x00000003, N_("Night Portrait")}, + {0x00000004, N_("Backlight")}, + {0x00000005, N_("Backlight Portrait")}, + {0x00000006, N_("Macro")}, + {0x00000007, N_("White")}, + {0x00000008, N_("Landscape")}, + {0x00000009, N_("Macro Text")}, + {0x0000000A, N_("BLSunset")}, + {0x0000000B, N_("Bluesky")}, + {0x0000000C, N_("Macro Portrait")}, + {0x0000000D, N_("Natural Green")}, + {0x0000000E, N_("Color")}, + {0x0000000F, N_("Color Hidden")}, + {0x00000010, N_("Tripod")}, + {0x00000011, N_("Action")}, + {0, NULL}}}, + { MNOTE_SAMSUNG_TAG_FACE_DETECTION, EXIF_FORMAT_LONG, + { {0x00000000, N_("FALSE")}, + {0x00000001, N_("TRUE")}, + {0, NULL}}}, + { MNOTE_SAMSUNG_TAG_FACE_RECOG, EXIF_FORMAT_LONG, + { {0x00000000, N_("FALSE")}, + {0x00000001, N_("TRUE")}, + {0, NULL}}}, + +#endif + { 0, 0, { { 0, NULL } } } +}; + +static const struct { + ExifTag tag; + ExifFormat fmt; + struct { + short index; + const char *string; + } elem[20]; +} subitems[] = { +#ifndef NO_VERBOSE_TAG_DATA + { MNOTE_SAMSUNG_SUBTAG_MODEL_ID_CLASS, EXIF_FORMAT_UNDEFINED, + { {0x1, N_("Essential")}, + {0x2, N_("PlusOnel")}, + {0x3, N_("Intelligent")}, + {0x4, N_("Style")}, + {0x5, N_("Wannabe")}, + {0x6, N_("Expertise")}, + {0x7, N_("NX")}, + {0x8, N_("GX")}, + {0x9, N_("HD")}, + {0xA, N_("SD")}, + {0, NULL}}}, + { MNOTE_SAMSUNG_SUBTAG_MODEL_ID_DEVEL, EXIF_FORMAT_UNDEFINED, + { {0x0, N_("OWN")}, + {0x7, N_("TSOE")}, + {0xA, N_("ODM")}, + {0, NULL}}}, + { MNOTE_SAMSUNG_SUBTAG_COLOR_ID, EXIF_FORMAT_SHORT, + { {0x0000, N_("Red")}, + {0x0100, N_("Yellow")}, + {0x0200, N_("Green")}, + {0x0300, N_("Blue")}, + {0x0400, N_("Magenta")}, + {0x0500, N_("Black")}, + {0x0600, N_("Gray")}, + {0x0700, N_("Un-classification")}, + {0, NULL}}}, +#endif + { 0, 0, { { 0, NULL } } } +}; + + +/*for setting data in an entry*/ +void mnote_samsung_entry_set_value_by_index (MnoteSamsungEntry *entry, int index) +{ + int i; + unsigned char* v; + + v = entry->data; + for (i = 0; (items[i].tag != entry->tag); i++); + exif_set_long(v, entry->order,(ExifLong)items[i].elem[index].index); +} + +void mnote_samsung_entry_set_value_by_subtag (MnoteSamsungEntry *entry, MnoteSamsungSubTag stag1, int sindex1, MnoteSamsungSubTag stag2, int sindex2, ExifShort sval) +{ + + unsigned char* v; + ExifLong result = 0; + int i; + + switch(entry->tag){ + case MNOTE_SAMSUNG_TAG_MODEL_ID: + v = entry->data; + for(i = 0 ; (subitems[i].tag != stag1) ; i++); + result |= subitems[i].elem[sindex1].index; + result <<= 4; + for(i = 0 ; (subitems[i].tag != stag2) ; i++); + result |= subitems[i].elem[sindex2].index; + result <<= 20; + result |= sval; + exif_set_long(v, entry->order, result); + break; + + case MNOTE_SAMSUNG_TAG_COLOR_INFO: + v = entry->data; + for(i = 0 ; (subitems[i].tag != stag1) ; i++); + result |= subitems[i].elem[sindex1].index; + result <<= 16; + result |= sval; + exif_set_long(v, entry->order, result); + break; + + default: + fprintf (stdout,_("inappropriate using mnote_samsung_entry_set_value_by_subtag - %i bytes"), entry->size); + break; + + } + +} + +void mnote_samsung_entry_set_value_by_string (MnoteSamsungEntry *entry, unsigned char* string, unsigned int len) +{ + /* for MNOTE_TAG_SERIAL_NUM */ + int i; + unsigned char* v; + + v = entry->data; + for (i = 0; (items[i].tag != entry->tag); i++); + if(items[i].elem[0].string == NULL) + strncpy(v, string, len); +} + +char *mnote_samsung_entry_get_value (const MnoteSamsungEntry *entry, char *v, unsigned int maxlen) +{ + char buf[30]={0}; + char v1[512]={0}; + size_t v1_maxlen= sizeof(v1); + ExifLong vl; + ExifShort vs = 0,vs1 = 0; + ExifRational vr; + ExifSRational vsr; + int i, j; + char c, c1; + double r; + + if (!entry) + return (NULL); + + memset (v, 0, maxlen); + maxlen--; + + if ((!entry->data) && (entry->components > 0)) + return (v); + + switch (entry->tag) { + + case MNOTE_SAMSUNG_TAG_MNOTE_VERSION: + CF (entry->format, EXIF_FORMAT_UNDEFINED, v, maxlen); + CC (entry->components, 4, v, maxlen); + vl = exif_get_long (entry->data, entry->order); + snprintf (v, maxlen, _("Samsung MakerNote Version: %li"), (long int)vl); + break; + + case MNOTE_SAMSUNG_TAG_DEVICE_ID: + CF (entry->format, EXIF_FORMAT_LONG, v, maxlen); + CC (entry->components, 1, v, maxlen); + vl = exif_get_long (entry->data, entry->order); + + for (i = 0; (items[i].tag != entry->tag); i++); + if (!items[i].tag) { + snprintf (v, maxlen, _("Internal error (unknown value %li)"),(long int) vl); + break; + } + CF (entry->format, items[i].fmt, v, maxlen); + /* find the value */ + for (j = 0; items[i].elem[j].string && (items[i].elem[j].index < vl); j++); + if (items[i].elem[j].index != vl) { + snprintf (v, maxlen, _("Unknown value %li"), (long int)vl); + break; + } + + snprintf (v, maxlen, _("Device ID: %s"), _(items[i].elem[j].string)); + break; + + case MNOTE_SAMSUNG_TAG_MODEL_ID: + CF (entry->format, EXIF_FORMAT_LONG, v, maxlen); + CC (entry->components, 1, v, maxlen); + vl = exif_get_long (entry->data, entry->order); + c = vl >> 24; /* Class info */ + c1 = vl >> 20; /* Development info */ + c1 = ~(c << 4) & c1; + vs = (ExifShort)(0x0000FFFF & vl); /* PID */ + + for (i = 0; (subitems[i].tag != MNOTE_SAMSUNG_SUBTAG_MODEL_ID_CLASS); i++); + CF (EXIF_FORMAT_UNDEFINED, subitems[i].fmt, v, maxlen); + /* find the value */ + for (j = 0; subitems[i].elem[j].string && (subitems[i].elem[j].index < c); j++); + if (subitems[i].elem[j].index != c ) { + snprintf (v, maxlen, _("Unknown Class info value %d in MNOTE_SAMSUNG_TAG_MODEL_ID"), c); + break; + } + snprintf (v, maxlen, _("Model ID: ClassInfo=%s, "), _(subitems[i].elem[j].string)); + + for (i = 0; (subitems[i].tag != MNOTE_SAMSUNG_SUBTAG_MODEL_ID_DEVEL); i++); + CF (EXIF_FORMAT_UNDEFINED, subitems[i].fmt, v, maxlen); + /* find the value */ + for (j = 0; subitems[i].elem[j].string && (subitems[i].elem[j].index < c1); j++); + if (subitems[i].elem[j].index != c1 ) { + snprintf (v, maxlen, _("Unknown Development info. value %d in MNOTE_SAMSUNG_TAG_MODEL_ID"), c1); + break; + } + snprintf (v1, v1_maxlen, _("DevelopmentInfo=%s, PID=%d"), _(subitems[i].elem[j].string), vs); + strncat (v, v1, strlen(v1)); + + break; + + case MNOTE_SAMSUNG_TAG_COLOR_INFO: + CF (entry->format, EXIF_FORMAT_SHORT, v, maxlen); + CC (entry->components, 2, v, maxlen); + vl = exif_get_long (entry->data, entry->order); + vs = vl >> 16; /* Color ID */ + vs1 = (ExifShort)(0x0000FFFF & vl); /* Color Score */ + + for (i = 0; (subitems[i].tag != MNOTE_SAMSUNG_SUBTAG_COLOR_ID); i++); + CF (EXIF_FORMAT_SHORT, subitems[i].fmt, v, maxlen); + /* find the value */ + for (j = 0; subitems[i].elem[j].string && (subitems[i].elem[j].index < vs); j++); + if (subitems[i].elem[j].index != vs ) { + snprintf (v, maxlen, _("Unknown Color ID value %d in MNOTE_SAMSUNG_TAG_COLOR_INFO"), vs); + break; + } + snprintf (v, maxlen, _("Color Info: ColorID=%s, ColorScore=0x%x"), _(subitems[i].elem[j].string), vs1); + break; + + case MNOTE_SAMSUNG_TAG_SERIAL_NUM: + CF (entry->format, EXIF_FORMAT_ASCII, v, maxlen); + strncpy (v1, (char *)entry->data, MIN(v1_maxlen, entry->size)); + snprintf(v, maxlen, _("Serial Number: %s"), _(v1)); + break; + + case MNOTE_SAMSUNG_TAG_IMAGE_COUNT: + case MNOTE_SAMSUNG_TAG_GPS_INFO01: + case MNOTE_SAMSUNG_TAG_GPS_INFO02: + case MNOTE_SAMSUNG_TAG_PREVIEW_IMAGE: + case MNOTE_SAMSUNG_TAG_FAVOR_TAGGING: + CF (entry->format, EXIF_FORMAT_LONG, v, maxlen); + CC (entry->components, 1, v, maxlen); + vl = exif_get_long (entry->data, entry->order); + + for (i = 0; (items[i].tag != entry->tag); i++); + + if (!items[i].tag) { + snprintf (v, maxlen, _("Internal error (unknown value %li)"), (long int)vl); + break; + } + CF (entry->format, items[i].fmt, v, maxlen); + /* find the value */ + for (j = 0; items[i].elem[j].string && (items[i].elem[j].index < vl); j++); + if (items[i].elem[j].index != vl) { + snprintf (v, maxlen, _("Unknown value %li"),(long int) vl); + break; + } + snprintf(v, maxlen, _("Favorite Tagging: %s"), _(items[i].elem[j].string)); + break; + + case MNOTE_SAMSUNG_TAG_SRW_COMPRESS: + CF (entry->format, EXIF_FORMAT_LONG, v, maxlen); + CC (entry->components, 1, v, maxlen); + vl = exif_get_long (entry->data, entry->order); + + for (i = 0; (items[i].tag != entry->tag); i++); + + if (!items[i].tag) { + snprintf (v, maxlen, _("Internal error (unknown value %li)"), (long int)vl); + break; + } + CF (entry->format, items[i].fmt, v, maxlen); + /* find the value */ + for (j = 0; items[i].elem[j].string && (items[i].elem[j].index < vl); j++); + if (items[i].elem[j].index != vl) { + snprintf (v, maxlen, _("Unknown value %li"),(long int) vl); + break; + } + snprintf(v, maxlen, _("SRW Compression: %s"), _(items[i].elem[j].string)); + break; + + case MNOTE_SAMSUNG_TAG_COLOR_SPACE: + CF (entry->format, EXIF_FORMAT_LONG, v, maxlen); + CC (entry->components, 1, v, maxlen); + vl = exif_get_long (entry->data, entry->order); + + for (i = 0; (items[i].tag != entry->tag); i++); + + if (!items[i].tag) { + snprintf (v, maxlen, _("Internal error (unknown value %li)"),(long int) vl); + break; + } + CF (entry->format, items[i].fmt, v, maxlen); + /* find the value */ + for (j = 0; items[i].elem[j].string && (items[i].elem[j].index < vl); j++); + if (items[i].elem[j].index != vl) { + snprintf (v, maxlen, _("Unknown value %li"),(long int) vl); + break; + } + snprintf(v, maxlen, _("Color Space: %s"), _(items[i].elem[j].string)); + break; + + case MNOTE_SAMSUNG_TAG_AE: + case MNOTE_SAMSUNG_TAG_AF: + case MNOTE_SAMSUNG_TAG_AWB01: + case MNOTE_SAMSUNG_TAG_AWB02: + case MNOTE_SAMSUNG_TAG_IPC: + case MNOTE_SAMSUNG_TAG_SCENE_RESULT: + CF (entry->format, EXIF_FORMAT_LONG, v, maxlen); + CC (entry->components, 1, v, maxlen); + vl = exif_get_long (entry->data, entry->order); + + for (i = 0; (items[i].tag != entry->tag); i++); + + if (!items[i].tag) { + snprintf (v, maxlen, _("Internal error (unknown value %li)"), (long int) vl); + break; + } + CF (entry->format, items[i].fmt, v, maxlen); + /* find the value */ + for (j = 0; items[i].elem[j].string && (items[i].elem[j].index < vl); j++); + if (items[i].elem[j].index != vl) { + snprintf (v, maxlen, _("Unknown value %li"), (long int) vl); + break; + } + snprintf(v, maxlen, _("Scene Result: %s"), _(items[i].elem[j].string)); + break; + + case MNOTE_SAMSUNG_TAG_SADEBUG_INFO01: + case MNOTE_SAMSUNG_TAG_SADEBUG_INFO02: + case MNOTE_SAMSUNG_TAG_FACE_DETECTION: + CF (entry->format, EXIF_FORMAT_LONG, v, maxlen); + CC (entry->components, 1, v, maxlen); + vl = exif_get_long (entry->data, entry->order); + + for (i = 0; (items[i].tag != entry->tag); i++); + + if (!items[i].tag) { + snprintf (v, maxlen, _("Internal error (unknown value %li)"), (long int) vl); + break; + } + CF (entry->format, items[i].fmt, v, maxlen); + /* find the value */ + for (j = 0; items[i].elem[j].string && (items[i].elem[j].index < vl); j++); + if (items[i].elem[j].index != vl) { + snprintf (v, maxlen, _("Unknown value %li"), (long int) vl); + break; + } + snprintf(v, maxlen, _("Face Detection: %s"), _(items[i].elem[j].string)); + break; + + case MNOTE_SAMSUNG_TAG_FACE_FEAT01: + case MNOTE_SAMSUNG_TAG_FACE_FEAT02: + case MNOTE_SAMSUNG_TAG_FACE_RECOG: + CF (entry->format, EXIF_FORMAT_LONG, v, maxlen); + CC (entry->components, 1, v, maxlen); + vl = exif_get_long (entry->data, entry->order); + + for (i = 0; (items[i].tag != entry->tag); i++); + + if (!items[i].tag) { + snprintf (v, maxlen, _("Internal error (unknown value %li)"),(long int) vl); + break; + } + CF (entry->format, items[i].fmt, v, maxlen); + /* find the value */ + for (j = 0; items[i].elem[j].string && (items[i].elem[j].index < vl); j++); + if (items[i].elem[j].index != vl) { + snprintf (v, maxlen, _("Unknown value %li"), (long int)vl); + break; + } + snprintf(v, maxlen, _("Face Recognition: %s"), _(items[i].elem[j].string)); + + break; + + case MNOTE_SAMSUNG_TAG_LENS_INFO: + case MNOTE_SAMSUNG_TAG_THIRDPARTY: + + + default: + switch (entry->format) { + case EXIF_FORMAT_ASCII: + strncpy (v, (char *)entry->data, MIN (maxlen, entry->size)); + break; + case EXIF_FORMAT_SHORT: + CC (entry->components, 1, v, maxlen); + vs = exif_get_short (entry->data, entry->order); + snprintf (v, maxlen, "%hu", vs); + break; + case EXIF_FORMAT_LONG: + CC (entry->components, 1, v, maxlen); + vl = exif_get_long (entry->data, entry->order); + snprintf (v, maxlen, "%li", (long int) vl); + break; + case EXIF_FORMAT_RATIONAL: + CC (entry->components, 1, v, maxlen); + vr = exif_get_rational (entry->data, entry->order); + if (!vr.denominator) { + strncpy (v, _("Infinite"), maxlen); + } else { + r = (double)vr.numerator / vr.denominator; + snprintf (v, maxlen, "%2.3f", r); + } + break; + case EXIF_FORMAT_SRATIONAL: + CC (entry->components, 1, v, maxlen); + vsr = exif_get_srational (entry->data, entry->order); + if (!vsr.denominator) { + strncpy (v, _("Infinite"), maxlen); + } else { + r = (double)vsr.numerator / vsr.denominator; + snprintf (v, maxlen, "%2.3f", r); + } + break; + case EXIF_FORMAT_UNDEFINED: + default: + snprintf (v, maxlen, _("%i bytes unknown data: "), + entry->size); + for (i = 0; i < (int)entry->size; i++) { + sprintf (buf, "%02x", entry->data[i]); + strncat (v, buf, maxlen - strlen (v)); + } + break; + } + break; + } + + return (v); +} diff --git a/libexif/samsung/mnote-samsung-entry.h b/libexif/samsung/mnote-samsung-entry.h new file mode 100644 index 0000000..7ba0ddd --- /dev/null +++ b/libexif/samsung/mnote-samsung-entry.h @@ -0,0 +1,52 @@ +/* + * libexif + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Sangchul Lee + * + * This library is free software; you can redistribute it and/or modify it under + * the terms of the GNU Lesser General Public License as published by the + * Free Software Foundation; either version 2.1 of the License, or (at your option) + * any later version. + * + * This library is distributed in the hope that it will be useful, but WITHOUT ANY + * WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this library; if not, write to the Free Software Foundation, Inc., 51 + * Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * + */ + +#ifndef __MNOTE_SAMSUNG_ENTRY_H__ +#define __MNOTE_SAMSUNG_ENTRY_H__ + +#include +#include +#include + +typedef struct _MnoteSamsungEntry MnoteSamsungEntry; + +struct _MnoteSamsungEntry { + MnoteSamsungTag tag; + ExifFormat format; + unsigned long components; + + unsigned char *data; + unsigned int size; + + ExifByteOrder order; +}; + +void mnote_samsung_entry_set_value_by_index (MnoteSamsungEntry *entry, int index); + +void mnote_samsung_entry_set_value_by_string (MnoteSamsungEntry *entry, unsigned char* string, unsigned int len); + +void mnote_samsung_entry_set_value_by_subtag (MnoteSamsungEntry *entry, MnoteSamsungSubTag stag1, int sindex1, MnoteSamsungSubTag stag2, int sindex2, ExifShort sval); + +char *mnote_samsung_entry_get_value (const MnoteSamsungEntry *, char *v, unsigned int maxlen); + +#endif /* __MNOTE_SAMSUNG_ENTRY_H__ */ diff --git a/libexif/samsung/mnote-samsung-tag.c b/libexif/samsung/mnote-samsung-tag.c new file mode 100644 index 0000000..d2bbc27 --- /dev/null +++ b/libexif/samsung/mnote-samsung-tag.c @@ -0,0 +1,102 @@ +/* + * libexif + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Sangchul Lee + * + * This library is free software; you can redistribute it and/or modify it under + * the terms of the GNU Lesser General Public License as published by the + * Free Software Foundation; either version 2.1 of the License, or (at your option) + * any later version. + * + * This library is distributed in the hope that it will be useful, but WITHOUT ANY + * WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this library; if not, write to the Free Software Foundation, Inc., 51 + * Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * + */ + +#include +#include "mnote-samsung-tag.h" + +#include + +#include + +static const struct { + MnoteSamsungTag tag; + const char *name; + const char *title; + const char *description; +} table[] = { +#ifndef NO_VERBOSE_TAG_STRINGS + {MNOTE_SAMSUNG_TAG_MNOTE_VERSION, "MakerNoteVersion", N_("Maker Note Version"), "1.0.0"}, + {MNOTE_SAMSUNG_TAG_DEVICE_ID, "SamsungDeviceID", N_("Samsung Device ID"), ""}, + {MNOTE_SAMSUNG_TAG_MODEL_ID, "SamsungModelID", N_("Samsung Model ID"), ""}, + {MNOTE_SAMSUNG_TAG_COLOR_INFO, "ColorInfo", N_("Color Info"), ""}, + {MNOTE_SAMSUNG_TAG_SERIAL_NUM, "ModelSerialNumber", N_("Model Serial Number"), ""}, + {MNOTE_SAMSUNG_TAG_IMAGE_COUNT, "ImageCount", N_("Image Count"), ""}, + {MNOTE_SAMSUNG_TAG_GPS_INFO01, "GPSInfo01", N_("GPS Infomation 01"), ""}, + {MNOTE_SAMSUNG_TAG_GPS_INFO02, "GPSInfo02", N_("GPS Infomation 02"), ""}, + {MNOTE_SAMSUNG_TAG_PREVIEW_IMAGE, "PreviewImageInfo", N_("Preview Image IFD Offset"), ""}, + {MNOTE_SAMSUNG_TAG_FAVOR_TAGGING, "FavoriteTagging", N_("Favorite Tagging"), ""}, + {MNOTE_SAMSUNG_TAG_SRW_COMPRESS, "SRWCompressionMode", N_("SRW Compression Mode"), ""}, + {MNOTE_SAMSUNG_TAG_COLOR_SPACE, "ColorSpace", N_("Color Space"), ""}, + {MNOTE_SAMSUNG_TAG_AE, "AE", N_("Auto Exposure"), ""}, + {MNOTE_SAMSUNG_TAG_AF, "AF", N_("Auto Focus"), ""}, + {MNOTE_SAMSUNG_TAG_AWB01, "AWB01", N_("Auto White Balance 01(Capture)"), ""}, + {MNOTE_SAMSUNG_TAG_AWB02, "AWB02", N_("Auto White Balance 02(Preview)"), ""}, + {MNOTE_SAMSUNG_TAG_IPC, "IPC", N_("Image Processing Chain"), ""}, + {MNOTE_SAMSUNG_TAG_SCENE_RESULT, "SceneResult", N_("Scene Recognition"), ""}, + {MNOTE_SAMSUNG_TAG_SADEBUG_INFO01, "SADebugInfo01", N_("Scene Recognition Debug Info 01"), ""}, + {MNOTE_SAMSUNG_TAG_SADEBUG_INFO02, "SADebugInfo02", N_("Scene Recognition Debug Info 02"), ""}, + {MNOTE_SAMSUNG_TAG_FACE_DETECTION, "FaceDetection", N_("Face Detection"), ""}, + {MNOTE_SAMSUNG_TAG_FACE_FEAT01, "FaceFeature01", N_("Face Feature 01"), ""}, + {MNOTE_SAMSUNG_TAG_FACE_FEAT02, "FaceFeature02", N_("Face Feature 02"), ""}, + {MNOTE_SAMSUNG_TAG_FACE_RECOG, "FaceRecognition", N_("Face Recognition"), ""}, + {MNOTE_SAMSUNG_TAG_LENS_INFO, "LensInfo", N_("Lens Infomation"), ""}, + {MNOTE_SAMSUNG_TAG_THIRDPARTY, "ThirdParty", N_("Ichikawa S/W"), ""}, + +#endif + {0, NULL, NULL, NULL} +}; + + +const char *mnote_samsung_tag_get_name (MnoteSamsungTag t) +{ + unsigned int i; + + for (i = 0; i < sizeof (table) / sizeof (table[0]); i++) + if (table[i].tag == t) return (table[i].name); + return NULL; +} + +const char *mnote_samsung_tag_get_title (MnoteSamsungTag t) +{ + unsigned int i; + + bindtextdomain (GETTEXT_PACKAGE, LOCALEDIR); + for (i = 0; i < sizeof (table) / sizeof (table[0]); i++) + if (table[i].tag == t) return (_(table[i].title)); + return NULL; +} + +const char *mnote_samsung_tag_get_description (MnoteSamsungTag t) +{ + unsigned int i; + + bindtextdomain (GETTEXT_PACKAGE, LOCALEDIR); + for (i = 0; i < sizeof (table) / sizeof (table[0]); i++) + if (table[i].tag == t) { + if (!*table[i].description) + return ""; + return (_(table[i].description)); + } + return NULL; +} + diff --git a/libexif/samsung/mnote-samsung-tag.h b/libexif/samsung/mnote-samsung-tag.h new file mode 100644 index 0000000..4a965c0 --- /dev/null +++ b/libexif/samsung/mnote-samsung-tag.h @@ -0,0 +1,84 @@ +/* + * libexif + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Sangchul Lee + * + * This library is free software; you can redistribute it and/or modify it under + * the terms of the GNU Lesser General Public License as published by the + * Free Software Foundation; either version 2.1 of the License, or (at your option) + * any later version. + * + * This library is distributed in the hope that it will be useful, but WITHOUT ANY + * WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this library; if not, write to the Free Software Foundation, Inc., 51 + * Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * + */ + +#ifndef __MNOTE_SAMSUNG_TAG_H__ +#define __MNOTE_SAMSUNG_TAG_H__ + +#include + +#ifdef __cplusplus +extern "C" { +#endif /* __cplusplus */ + +enum _MnoteSamsungTag { + MNOTE_SAMSUNG_TAG_MNOTE_VERSION = 0x01, + MNOTE_SAMSUNG_TAG_DEVICE_ID = 0x02, + MNOTE_SAMSUNG_TAG_MODEL_ID = 0x03, + MNOTE_SAMSUNG_TAG_COLOR_INFO = 0x20, + MNOTE_SAMSUNG_TAG_SERIAL_NUM = 0x23, + MNOTE_SAMSUNG_TAG_IMAGE_COUNT = 0x25, + MNOTE_SAMSUNG_TAG_GPS_INFO01 = 0x30, + MNOTE_SAMSUNG_TAG_GPS_INFO02 = 0x31, + MNOTE_SAMSUNG_TAG_PREVIEW_IMAGE = 0x35, + MNOTE_SAMSUNG_TAG_FAVOR_TAGGING = 0x40, + MNOTE_SAMSUNG_TAG_SRW_COMPRESS = 0x45, + MNOTE_SAMSUNG_TAG_COLOR_SPACE = 0x50, + MNOTE_SAMSUNG_TAG_AE = 0x60, + MNOTE_SAMSUNG_TAG_AF = 0x80, + MNOTE_SAMSUNG_TAG_AWB01 = 0xa0, + MNOTE_SAMSUNG_TAG_AWB02 = 0xa1, + MNOTE_SAMSUNG_TAG_IPC = 0xc0, + MNOTE_SAMSUNG_TAG_SCENE_RESULT = 0xe0, + MNOTE_SAMSUNG_TAG_SADEBUG_INFO01= 0xe1, + MNOTE_SAMSUNG_TAG_SADEBUG_INFO02= 0xe2, + MNOTE_SAMSUNG_TAG_FACE_DETECTION= 0x100, + MNOTE_SAMSUNG_TAG_FACE_FEAT01 = 0x101, + MNOTE_SAMSUNG_TAG_FACE_FEAT02 = 0x102, + MNOTE_SAMSUNG_TAG_FACE_RECOG = 0x120, + MNOTE_SAMSUNG_TAG_LENS_INFO = 0x140, + MNOTE_SAMSUNG_TAG_THIRDPARTY = 0xa000 +}; +typedef enum _MnoteSamsungTag MnoteSamsungTag; + +enum _MnoteSamsungSubTag { + MNOTE_SAMSUNG_SUBTAG_MODEL_ID_CLASS = 0x201, + MNOTE_SAMSUNG_SUBTAG_MODEL_ID_DEVEL = 0x202, + MNOTE_SAMSUNG_SUBTAG_COLOR_ID = 0x211 +}; +typedef enum _MnoteSamsungSubTag MnoteSamsungSubTag; + + + +const char *mnote_samsung_tag_get_name (MnoteSamsungTag); + +const char *mnote_samsung_tag_get_title (MnoteSamsungTag); + +const char *mnote_samsung_tag_get_description (MnoteSamsungTag); + + + +#ifdef __cplusplus +} +#endif /* __cplusplus */ + +#endif /* __MNOTE_SAMSUNG_TAG_H__ */ diff --git a/packaging/libexif.changes b/packaging/libexif.changes index c3babe6..430c576 100644 --- a/packaging/libexif.changes +++ b/packaging/libexif.changes @@ -1,3 +1,6 @@ +* Thu Jun 20 2013 Anas Nashif accepted/tizen/20130520.095854@235995e +- add samsung device support + * Sat May 11 2013 Anas Nashif submit/tizen/20130509.181038@c5bd43f - Set license using %license diff --git a/packaging/libexif.spec b/packaging/libexif.spec index 4aa9687..15c3ebf 100644 --- a/packaging/libexif.spec +++ b/packaging/libexif.spec @@ -9,6 +9,7 @@ Source: %{name}-%{version}.tar.bz2 Source1: baselibs.conf BuildRequires: doxygen BuildRequires: pkg-config +BuildRequires: gettext-tools %define debug_package_requires %{name} = %{version}-%{release} @@ -30,10 +31,11 @@ digital cameras. %setup -q %build -%configure --with-pic \ +%reconfigure --with-pic \ --disable-static \ --with-doc-dir=%{_docdir}/%{name} -make %{?_smp_mflags} +make +### %{?_smp_mflags} %check make check -- 2.7.4