/ext/exif/exif.c
C | 4774 lines | 3938 code | 389 blank | 447 comment | 551 complexity | dcd51ab244edc17aa4832200838a8ba3 MD5 | raw file
Possible License(s): BSD-2-Clause, BSD-3-Clause, MPL-2.0-no-copyleft-exception, LGPL-2.1
Large files files are truncated, but you can click here to view the full file
- /*
- +----------------------------------------------------------------------+
- | Copyright (c) The PHP Group |
- +----------------------------------------------------------------------+
- | This source file is subject to version 3.01 of the PHP license, |
- | that is bundled with this package in the file LICENSE, and is |
- | available through the world-wide-web at the following url: |
- | http://www.php.net/license/3_01.txt |
- | If you did not receive a copy of the PHP license and are unable to |
- | obtain it through the world-wide-web, please send a note to |
- | license@php.net so we can mail you a copy immediately. |
- +----------------------------------------------------------------------+
- | Authors: Rasmus Lerdorf <rasmus@php.net> |
- | Marcus Boerger <helly@php.net> |
- +----------------------------------------------------------------------+
- */
- #ifdef HAVE_CONFIG_H
- #include "config.h"
- #endif
- #include "php.h"
- #include "ext/standard/file.h"
- #if HAVE_EXIF
- /* When EXIF_DEBUG is defined the module generates a lot of debug messages
- * that help understanding what is going on. This can and should be used
- * while extending the module as it shows if you are at the right position.
- * You are always considered to have a copy of TIFF6.0 and EXIF2.10 standard.
- */
- #undef EXIF_DEBUG
- #ifdef EXIF_DEBUG
- #define EXIFERR_DC , const char *_file, size_t _line
- #define EXIFERR_CC , __FILE__, __LINE__
- #else
- #define EXIFERR_DC
- #define EXIFERR_CC
- #endif
- #include "php_exif.h"
- #include "exif_arginfo.h"
- #include <math.h>
- #include "php_ini.h"
- #include "ext/standard/php_string.h"
- #include "ext/standard/php_image.h"
- #include "ext/standard/info.h"
- /* needed for ssize_t definition */
- #include <sys/types.h>
- #ifdef __SANITIZE_ADDRESS__
- # include <sanitizer/asan_interface.h>
- #endif
- typedef unsigned char uchar;
- #ifndef TRUE
- # define TRUE 1
- # define FALSE 0
- #endif
- #ifndef max
- # define max(a,b) ((a)>(b) ? (a) : (b))
- #endif
- #define EFREE_IF(ptr) if (ptr) efree(ptr)
- #define MAX_IFD_NESTING_LEVEL 150
- /* {{{ PHP_MINFO_FUNCTION
- */
- PHP_MINFO_FUNCTION(exif)
- {
- php_info_print_table_start();
- php_info_print_table_row(2, "EXIF Support", "enabled");
- php_info_print_table_row(2, "Supported EXIF Version", "0220");
- php_info_print_table_row(2, "Supported filetypes", "JPEG, TIFF");
- if (zend_hash_str_exists(&module_registry, "mbstring", sizeof("mbstring")-1)) {
- php_info_print_table_row(2, "Multibyte decoding support using mbstring", "enabled");
- } else {
- php_info_print_table_row(2, "Multibyte decoding support using mbstring", "disabled");
- }
- php_info_print_table_row(2, "Extended EXIF tag formats", "Canon, Casio, Fujifilm, Nikon, Olympus, Samsung, Panasonic, DJI, Sony, Pentax, Minolta, Sigma, Foveon, Kyocera, Ricoh, AGFA, Epson");
- php_info_print_table_end();
- DISPLAY_INI_ENTRIES();
- }
- /* }}} */
- ZEND_BEGIN_MODULE_GLOBALS(exif)
- char * encode_unicode;
- char * decode_unicode_be;
- char * decode_unicode_le;
- char * encode_jis;
- char * decode_jis_be;
- char * decode_jis_le;
- HashTable *tag_table_cache;
- ZEND_END_MODULE_GLOBALS(exif)
- ZEND_DECLARE_MODULE_GLOBALS(exif)
- #define EXIF_G(v) ZEND_MODULE_GLOBALS_ACCESSOR(exif, v)
- #if defined(ZTS) && defined(COMPILE_DL_EXIF)
- ZEND_TSRMLS_CACHE_DEFINE()
- #endif
- /* {{{ PHP_INI
- */
- ZEND_INI_MH(OnUpdateEncode)
- {
- if (new_value && ZSTR_LEN(new_value)) {
- const zend_encoding **return_list;
- size_t return_size;
- if (FAILURE == zend_multibyte_parse_encoding_list(ZSTR_VAL(new_value), ZSTR_LEN(new_value),
- &return_list, &return_size, 0)) {
- php_error_docref(NULL, E_WARNING, "Illegal encoding ignored: '%s'", ZSTR_VAL(new_value));
- return FAILURE;
- }
- pefree((void *) return_list, 0);
- }
- return OnUpdateString(entry, new_value, mh_arg1, mh_arg2, mh_arg3, stage);
- }
- ZEND_INI_MH(OnUpdateDecode)
- {
- if (new_value) {
- const zend_encoding **return_list;
- size_t return_size;
- if (FAILURE == zend_multibyte_parse_encoding_list(ZSTR_VAL(new_value), ZSTR_LEN(new_value),
- &return_list, &return_size, 0)) {
- php_error_docref(NULL, E_WARNING, "Illegal encoding ignored: '%s'", ZSTR_VAL(new_value));
- return FAILURE;
- }
- pefree((void *) return_list, 0);
- }
- return OnUpdateString(entry, new_value, mh_arg1, mh_arg2, mh_arg3, stage);
- }
- PHP_INI_BEGIN()
- STD_PHP_INI_ENTRY("exif.encode_unicode", "ISO-8859-15", PHP_INI_ALL, OnUpdateEncode, encode_unicode, zend_exif_globals, exif_globals)
- STD_PHP_INI_ENTRY("exif.decode_unicode_motorola", "UCS-2BE", PHP_INI_ALL, OnUpdateDecode, decode_unicode_be, zend_exif_globals, exif_globals)
- STD_PHP_INI_ENTRY("exif.decode_unicode_intel", "UCS-2LE", PHP_INI_ALL, OnUpdateDecode, decode_unicode_le, zend_exif_globals, exif_globals)
- STD_PHP_INI_ENTRY("exif.encode_jis", "", PHP_INI_ALL, OnUpdateEncode, encode_jis, zend_exif_globals, exif_globals)
- STD_PHP_INI_ENTRY("exif.decode_jis_motorola", "JIS", PHP_INI_ALL, OnUpdateDecode, decode_jis_be, zend_exif_globals, exif_globals)
- STD_PHP_INI_ENTRY("exif.decode_jis_intel", "JIS", PHP_INI_ALL, OnUpdateDecode, decode_jis_le, zend_exif_globals, exif_globals)
- PHP_INI_END()
- /* }}} */
- /* {{{ PHP_GINIT_FUNCTION
- */
- static PHP_GINIT_FUNCTION(exif)
- {
- #if defined(COMPILE_DL_EXIF) && defined(ZTS)
- ZEND_TSRMLS_CACHE_UPDATE();
- #endif
- exif_globals->encode_unicode = NULL;
- exif_globals->decode_unicode_be = NULL;
- exif_globals->decode_unicode_le = NULL;
- exif_globals->encode_jis = NULL;
- exif_globals->decode_jis_be = NULL;
- exif_globals->decode_jis_le = NULL;
- exif_globals->tag_table_cache = NULL;
- }
- /* }}} */
- /* {{{ PHP_MINIT_FUNCTION(exif)
- */
- PHP_MINIT_FUNCTION(exif)
- {
- REGISTER_INI_ENTRIES();
- if (zend_hash_str_exists(&module_registry, "mbstring", sizeof("mbstring")-1)) {
- REGISTER_LONG_CONSTANT("EXIF_USE_MBSTRING", 1, CONST_CS | CONST_PERSISTENT);
- } else {
- REGISTER_LONG_CONSTANT("EXIF_USE_MBSTRING", 0, CONST_CS | CONST_PERSISTENT);
- }
- return SUCCESS;
- }
- /* }}} */
- /* {{{ PHP_MSHUTDOWN_FUNCTION
- */
- PHP_MSHUTDOWN_FUNCTION(exif)
- {
- UNREGISTER_INI_ENTRIES();
- if (EXIF_G(tag_table_cache)) {
- zend_hash_destroy(EXIF_G(tag_table_cache));
- free(EXIF_G(tag_table_cache));
- }
- return SUCCESS;
- }
- /* }}} */
- /* {{{ exif dependencies */
- static const zend_module_dep exif_module_deps[] = {
- ZEND_MOD_REQUIRED("standard")
- ZEND_MOD_OPTIONAL("mbstring")
- ZEND_MOD_END
- };
- /* }}} */
- /* {{{ exif_module_entry
- */
- zend_module_entry exif_module_entry = {
- STANDARD_MODULE_HEADER_EX, NULL,
- exif_module_deps,
- "exif",
- ext_functions,
- PHP_MINIT(exif),
- PHP_MSHUTDOWN(exif),
- NULL, NULL,
- PHP_MINFO(exif),
- PHP_EXIF_VERSION,
- PHP_MODULE_GLOBALS(exif),
- PHP_GINIT(exif),
- NULL,
- NULL,
- STANDARD_MODULE_PROPERTIES_EX
- };
- /* }}} */
- #ifdef COMPILE_DL_EXIF
- ZEND_GET_MODULE(exif)
- #endif
- /* {{{ php_strnlen
- * get length of string if buffer if less than buffer size or buffer size */
- static size_t php_strnlen(char* str, size_t maxlen) {
- size_t len = 0;
- if (str && maxlen && *str) {
- do {
- len++;
- } while (--maxlen && *(++str));
- }
- return len;
- }
- /* }}} */
- /* {{{ error messages
- */
- static const char * EXIF_ERROR_FILEEOF = "Unexpected end of file reached";
- static const char * EXIF_ERROR_CORRUPT = "File structure corrupted";
- static const char * EXIF_ERROR_THUMBEOF = "Thumbnail goes IFD boundary or end of file reached";
- static const char * EXIF_ERROR_FSREALLOC = "Illegal reallocating of undefined file section";
- #define EXIF_ERRLOG_FILEEOF(ImageInfo) exif_error_docref(NULL EXIFERR_CC, ImageInfo, E_WARNING, "%s", EXIF_ERROR_FILEEOF);
- #define EXIF_ERRLOG_CORRUPT(ImageInfo) exif_error_docref(NULL EXIFERR_CC, ImageInfo, E_WARNING, "%s", EXIF_ERROR_CORRUPT);
- #define EXIF_ERRLOG_THUMBEOF(ImageInfo) exif_error_docref(NULL EXIFERR_CC, ImageInfo, E_WARNING, "%s", EXIF_ERROR_THUMBEOF);
- #define EXIF_ERRLOG_FSREALLOC(ImageInfo) exif_error_docref(NULL EXIFERR_CC, ImageInfo, E_WARNING, "%s", EXIF_ERROR_FSREALLOC);
- /* }}} */
- /* {{{ format description defines
- Describes format descriptor
- */
- static int php_tiff_bytes_per_format[] = {0, 1, 1, 2, 4, 8, 1, 1, 2, 4, 8, 4, 8, 1};
- #define NUM_FORMATS 13
- #define TAG_FMT_BYTE 1
- #define TAG_FMT_STRING 2
- #define TAG_FMT_USHORT 3
- #define TAG_FMT_ULONG 4
- #define TAG_FMT_URATIONAL 5
- #define TAG_FMT_SBYTE 6
- #define TAG_FMT_UNDEFINED 7
- #define TAG_FMT_SSHORT 8
- #define TAG_FMT_SLONG 9
- #define TAG_FMT_SRATIONAL 10
- #define TAG_FMT_SINGLE 11
- #define TAG_FMT_DOUBLE 12
- #define TAG_FMT_IFD 13
- #ifdef EXIF_DEBUG
- static char *exif_get_tagformat(int format)
- {
- switch(format) {
- case TAG_FMT_BYTE: return "BYTE";
- case TAG_FMT_STRING: return "STRING";
- case TAG_FMT_USHORT: return "USHORT";
- case TAG_FMT_ULONG: return "ULONG";
- case TAG_FMT_URATIONAL: return "URATIONAL";
- case TAG_FMT_SBYTE: return "SBYTE";
- case TAG_FMT_UNDEFINED: return "UNDEFINED";
- case TAG_FMT_SSHORT: return "SSHORT";
- case TAG_FMT_SLONG: return "SLONG";
- case TAG_FMT_SRATIONAL: return "SRATIONAL";
- case TAG_FMT_SINGLE: return "SINGLE";
- case TAG_FMT_DOUBLE: return "DOUBLE";
- case TAG_FMT_IFD: return "IFD";
- }
- return "*Illegal";
- }
- #endif
- /* Describes tag values */
- #define TAG_GPS_VERSION_ID 0x0000
- #define TAG_GPS_LATITUDE_REF 0x0001
- #define TAG_GPS_LATITUDE 0x0002
- #define TAG_GPS_LONGITUDE_REF 0x0003
- #define TAG_GPS_LONGITUDE 0x0004
- #define TAG_GPS_ALTITUDE_REF 0x0005
- #define TAG_GPS_ALTITUDE 0x0006
- #define TAG_GPS_TIME_STAMP 0x0007
- #define TAG_GPS_SATELLITES 0x0008
- #define TAG_GPS_STATUS 0x0009
- #define TAG_GPS_MEASURE_MODE 0x000A
- #define TAG_GPS_DOP 0x000B
- #define TAG_GPS_SPEED_REF 0x000C
- #define TAG_GPS_SPEED 0x000D
- #define TAG_GPS_TRACK_REF 0x000E
- #define TAG_GPS_TRACK 0x000F
- #define TAG_GPS_IMG_DIRECTION_REF 0x0010
- #define TAG_GPS_IMG_DIRECTION 0x0011
- #define TAG_GPS_MAP_DATUM 0x0012
- #define TAG_GPS_DEST_LATITUDE_REF 0x0013
- #define TAG_GPS_DEST_LATITUDE 0x0014
- #define TAG_GPS_DEST_LONGITUDE_REF 0x0015
- #define TAG_GPS_DEST_LONGITUDE 0x0016
- #define TAG_GPS_DEST_BEARING_REF 0x0017
- #define TAG_GPS_DEST_BEARING 0x0018
- #define TAG_GPS_DEST_DISTANCE_REF 0x0019
- #define TAG_GPS_DEST_DISTANCE 0x001A
- #define TAG_GPS_PROCESSING_METHOD 0x001B
- #define TAG_GPS_AREA_INFORMATION 0x001C
- #define TAG_GPS_DATE_STAMP 0x001D
- #define TAG_GPS_DIFFERENTIAL 0x001E
- #define TAG_TIFF_COMMENT 0x00FE /* SHOULDN'T HAPPEN */
- #define TAG_NEW_SUBFILE 0x00FE /* New version of subfile tag */
- #define TAG_SUBFILE_TYPE 0x00FF /* Old version of subfile tag */
- #define TAG_IMAGEWIDTH 0x0100
- #define TAG_IMAGEHEIGHT 0x0101
- #define TAG_BITS_PER_SAMPLE 0x0102
- #define TAG_COMPRESSION 0x0103
- #define TAG_PHOTOMETRIC_INTERPRETATION 0x0106
- #define TAG_TRESHHOLDING 0x0107
- #define TAG_CELL_WIDTH 0x0108
- #define TAG_CELL_HEIGHT 0x0109
- #define TAG_FILL_ORDER 0x010A
- #define TAG_DOCUMENT_NAME 0x010D
- #define TAG_IMAGE_DESCRIPTION 0x010E
- #define TAG_MAKE 0x010F
- #define TAG_MODEL 0x0110
- #define TAG_STRIP_OFFSETS 0x0111
- #define TAG_ORIENTATION 0x0112
- #define TAG_SAMPLES_PER_PIXEL 0x0115
- #define TAG_ROWS_PER_STRIP 0x0116
- #define TAG_STRIP_BYTE_COUNTS 0x0117
- #define TAG_MIN_SAMPPLE_VALUE 0x0118
- #define TAG_MAX_SAMPLE_VALUE 0x0119
- #define TAG_X_RESOLUTION 0x011A
- #define TAG_Y_RESOLUTION 0x011B
- #define TAG_PLANAR_CONFIGURATION 0x011C
- #define TAG_PAGE_NAME 0x011D
- #define TAG_X_POSITION 0x011E
- #define TAG_Y_POSITION 0x011F
- #define TAG_FREE_OFFSETS 0x0120
- #define TAG_FREE_BYTE_COUNTS 0x0121
- #define TAG_GRAY_RESPONSE_UNIT 0x0122
- #define TAG_GRAY_RESPONSE_CURVE 0x0123
- #define TAG_RESOLUTION_UNIT 0x0128
- #define TAG_PAGE_NUMBER 0x0129
- #define TAG_TRANSFER_FUNCTION 0x012D
- #define TAG_SOFTWARE 0x0131
- #define TAG_DATETIME 0x0132
- #define TAG_ARTIST 0x013B
- #define TAG_HOST_COMPUTER 0x013C
- #define TAG_PREDICTOR 0x013D
- #define TAG_WHITE_POINT 0x013E
- #define TAG_PRIMARY_CHROMATICITIES 0x013F
- #define TAG_COLOR_MAP 0x0140
- #define TAG_HALFTONE_HINTS 0x0141
- #define TAG_TILE_WIDTH 0x0142
- #define TAG_TILE_LENGTH 0x0143
- #define TAG_TILE_OFFSETS 0x0144
- #define TAG_TILE_BYTE_COUNTS 0x0145
- #define TAG_SUB_IFD 0x014A
- #define TAG_INK_SETMPUTER 0x014C
- #define TAG_INK_NAMES 0x014D
- #define TAG_NUMBER_OF_INKS 0x014E
- #define TAG_DOT_RANGE 0x0150
- #define TAG_TARGET_PRINTER 0x0151
- #define TAG_EXTRA_SAMPLE 0x0152
- #define TAG_SAMPLE_FORMAT 0x0153
- #define TAG_S_MIN_SAMPLE_VALUE 0x0154
- #define TAG_S_MAX_SAMPLE_VALUE 0x0155
- #define TAG_TRANSFER_RANGE 0x0156
- #define TAG_JPEG_TABLES 0x015B
- #define TAG_JPEG_PROC 0x0200
- #define TAG_JPEG_INTERCHANGE_FORMAT 0x0201
- #define TAG_JPEG_INTERCHANGE_FORMAT_LEN 0x0202
- #define TAG_JPEG_RESTART_INTERVAL 0x0203
- #define TAG_JPEG_LOSSLESS_PREDICTOR 0x0205
- #define TAG_JPEG_POINT_TRANSFORMS 0x0206
- #define TAG_JPEG_Q_TABLES 0x0207
- #define TAG_JPEG_DC_TABLES 0x0208
- #define TAG_JPEG_AC_TABLES 0x0209
- #define TAG_YCC_COEFFICIENTS 0x0211
- #define TAG_YCC_SUB_SAMPLING 0x0212
- #define TAG_YCC_POSITIONING 0x0213
- #define TAG_REFERENCE_BLACK_WHITE 0x0214
- /* 0x0301 - 0x0302 */
- /* 0x0320 */
- /* 0x0343 */
- /* 0x5001 - 0x501B */
- /* 0x5021 - 0x503B */
- /* 0x5090 - 0x5091 */
- /* 0x5100 - 0x5101 */
- /* 0x5110 - 0x5113 */
- /* 0x80E3 - 0x80E6 */
- /* 0x828d - 0x828F */
- #define TAG_COPYRIGHT 0x8298
- #define TAG_EXPOSURETIME 0x829A
- #define TAG_FNUMBER 0x829D
- #define TAG_EXIF_IFD_POINTER 0x8769
- #define TAG_ICC_PROFILE 0x8773
- #define TAG_EXPOSURE_PROGRAM 0x8822
- #define TAG_SPECTRAL_SENSITY 0x8824
- #define TAG_GPS_IFD_POINTER 0x8825
- #define TAG_ISOSPEED 0x8827
- #define TAG_OPTOELECTRIC_CONVERSION_F 0x8828
- /* 0x8829 - 0x882b */
- #define TAG_EXIFVERSION 0x9000
- #define TAG_DATE_TIME_ORIGINAL 0x9003
- #define TAG_DATE_TIME_DIGITIZED 0x9004
- #define TAG_COMPONENT_CONFIG 0x9101
- #define TAG_COMPRESSED_BITS_PER_PIXEL 0x9102
- #define TAG_SHUTTERSPEED 0x9201
- #define TAG_APERTURE 0x9202
- #define TAG_BRIGHTNESS_VALUE 0x9203
- #define TAG_EXPOSURE_BIAS_VALUE 0x9204
- #define TAG_MAX_APERTURE 0x9205
- #define TAG_SUBJECT_DISTANCE 0x9206
- #define TAG_METRIC_MODULE 0x9207
- #define TAG_LIGHT_SOURCE 0x9208
- #define TAG_FLASH 0x9209
- #define TAG_FOCAL_LENGTH 0x920A
- /* 0x920B - 0x920D */
- /* 0x9211 - 0x9216 */
- #define TAG_SUBJECT_AREA 0x9214
- #define TAG_MAKER_NOTE 0x927C
- #define TAG_USERCOMMENT 0x9286
- #define TAG_SUB_SEC_TIME 0x9290
- #define TAG_SUB_SEC_TIME_ORIGINAL 0x9291
- #define TAG_SUB_SEC_TIME_DIGITIZED 0x9292
- /* 0x923F */
- /* 0x935C */
- #define TAG_XP_TITLE 0x9C9B
- #define TAG_XP_COMMENTS 0x9C9C
- #define TAG_XP_AUTHOR 0x9C9D
- #define TAG_XP_KEYWORDS 0x9C9E
- #define TAG_XP_SUBJECT 0x9C9F
- #define TAG_FLASH_PIX_VERSION 0xA000
- #define TAG_COLOR_SPACE 0xA001
- #define TAG_COMP_IMAGE_WIDTH 0xA002 /* compressed images only */
- #define TAG_COMP_IMAGE_HEIGHT 0xA003
- #define TAG_RELATED_SOUND_FILE 0xA004
- #define TAG_INTEROP_IFD_POINTER 0xA005 /* IFD pointer */
- #define TAG_FLASH_ENERGY 0xA20B
- #define TAG_SPATIAL_FREQUENCY_RESPONSE 0xA20C
- #define TAG_FOCALPLANE_X_RES 0xA20E
- #define TAG_FOCALPLANE_Y_RES 0xA20F
- #define TAG_FOCALPLANE_RESOLUTION_UNIT 0xA210
- #define TAG_SUBJECT_LOCATION 0xA214
- #define TAG_EXPOSURE_INDEX 0xA215
- #define TAG_SENSING_METHOD 0xA217
- #define TAG_FILE_SOURCE 0xA300
- #define TAG_SCENE_TYPE 0xA301
- #define TAG_CFA_PATTERN 0xA302
- #define TAG_CUSTOM_RENDERED 0xA401
- #define TAG_EXPOSURE_MODE 0xA402
- #define TAG_WHITE_BALANCE 0xA403
- #define TAG_DIGITAL_ZOOM_RATIO 0xA404
- #define TAG_FOCAL_LENGTH_IN_35_MM_FILM 0xA405
- #define TAG_SCENE_CAPTURE_TYPE 0xA406
- #define TAG_GAIN_CONTROL 0xA407
- #define TAG_CONTRAST 0xA408
- #define TAG_SATURATION 0xA409
- #define TAG_SHARPNESS 0xA40A
- #define TAG_DEVICE_SETTING_DESCRIPTION 0xA40B
- #define TAG_SUBJECT_DISTANCE_RANGE 0xA40C
- #define TAG_IMAGE_UNIQUE_ID 0xA420
- /* Olympus specific tags */
- #define TAG_OLYMPUS_SPECIALMODE 0x0200
- #define TAG_OLYMPUS_JPEGQUAL 0x0201
- #define TAG_OLYMPUS_MACRO 0x0202
- #define TAG_OLYMPUS_DIGIZOOM 0x0204
- #define TAG_OLYMPUS_SOFTWARERELEASE 0x0207
- #define TAG_OLYMPUS_PICTINFO 0x0208
- #define TAG_OLYMPUS_CAMERAID 0x0209
- /* end Olympus specific tags */
- /* Internal */
- #define TAG_NONE -1 /* note that -1 <> 0xFFFF */
- #define TAG_COMPUTED_VALUE -2
- #define TAG_END_OF_LIST 0xFFFD
- /* Values for TAG_PHOTOMETRIC_INTERPRETATION */
- #define PMI_BLACK_IS_ZERO 0
- #define PMI_WHITE_IS_ZERO 1
- #define PMI_RGB 2
- #define PMI_PALETTE_COLOR 3
- #define PMI_TRANSPARENCY_MASK 4
- #define PMI_SEPARATED 5
- #define PMI_YCBCR 6
- #define PMI_CIELAB 8
- /* }}} */
- /* {{{ TabTable[]
- */
- typedef const struct {
- unsigned short Tag;
- char *Desc;
- } tag_info_type;
- typedef tag_info_type tag_info_array[];
- typedef tag_info_type *tag_table_type;
- #define TAG_TABLE_END \
- {TAG_NONE, "No tag value"},\
- {TAG_COMPUTED_VALUE, "Computed value"},\
- {TAG_END_OF_LIST, ""} /* Important for exif_get_tagname() IF value != "" function result is != false */
- static tag_info_array tag_table_IFD = {
- { 0x000B, "ACDComment"},
- { 0x00FE, "NewSubFile"}, /* better name it 'ImageType' ? */
- { 0x00FF, "SubFile"},
- { 0x0100, "ImageWidth"},
- { 0x0101, "ImageLength"},
- { 0x0102, "BitsPerSample"},
- { 0x0103, "Compression"},
- { 0x0106, "PhotometricInterpretation"},
- { 0x010A, "FillOrder"},
- { 0x010D, "DocumentName"},
- { 0x010E, "ImageDescription"},
- { 0x010F, "Make"},
- { 0x0110, "Model"},
- { 0x0111, "StripOffsets"},
- { 0x0112, "Orientation"},
- { 0x0115, "SamplesPerPixel"},
- { 0x0116, "RowsPerStrip"},
- { 0x0117, "StripByteCounts"},
- { 0x0118, "MinSampleValue"},
- { 0x0119, "MaxSampleValue"},
- { 0x011A, "XResolution"},
- { 0x011B, "YResolution"},
- { 0x011C, "PlanarConfiguration"},
- { 0x011D, "PageName"},
- { 0x011E, "XPosition"},
- { 0x011F, "YPosition"},
- { 0x0120, "FreeOffsets"},
- { 0x0121, "FreeByteCounts"},
- { 0x0122, "GrayResponseUnit"},
- { 0x0123, "GrayResponseCurve"},
- { 0x0124, "T4Options"},
- { 0x0125, "T6Options"},
- { 0x0128, "ResolutionUnit"},
- { 0x0129, "PageNumber"},
- { 0x012D, "TransferFunction"},
- { 0x0131, "Software"},
- { 0x0132, "DateTime"},
- { 0x013B, "Artist"},
- { 0x013C, "HostComputer"},
- { 0x013D, "Predictor"},
- { 0x013E, "WhitePoint"},
- { 0x013F, "PrimaryChromaticities"},
- { 0x0140, "ColorMap"},
- { 0x0141, "HalfToneHints"},
- { 0x0142, "TileWidth"},
- { 0x0143, "TileLength"},
- { 0x0144, "TileOffsets"},
- { 0x0145, "TileByteCounts"},
- { 0x014A, "SubIFD"},
- { 0x014C, "InkSet"},
- { 0x014D, "InkNames"},
- { 0x014E, "NumberOfInks"},
- { 0x0150, "DotRange"},
- { 0x0151, "TargetPrinter"},
- { 0x0152, "ExtraSample"},
- { 0x0153, "SampleFormat"},
- { 0x0154, "SMinSampleValue"},
- { 0x0155, "SMaxSampleValue"},
- { 0x0156, "TransferRange"},
- { 0x0157, "ClipPath"},
- { 0x0158, "XClipPathUnits"},
- { 0x0159, "YClipPathUnits"},
- { 0x015A, "Indexed"},
- { 0x015B, "JPEGTables"},
- { 0x015F, "OPIProxy"},
- { 0x0200, "JPEGProc"},
- { 0x0201, "JPEGInterchangeFormat"},
- { 0x0202, "JPEGInterchangeFormatLength"},
- { 0x0203, "JPEGRestartInterval"},
- { 0x0205, "JPEGLosslessPredictors"},
- { 0x0206, "JPEGPointTransforms"},
- { 0x0207, "JPEGQTables"},
- { 0x0208, "JPEGDCTables"},
- { 0x0209, "JPEGACTables"},
- { 0x0211, "YCbCrCoefficients"},
- { 0x0212, "YCbCrSubSampling"},
- { 0x0213, "YCbCrPositioning"},
- { 0x0214, "ReferenceBlackWhite"},
- { 0x02BC, "ExtensibleMetadataPlatform"}, /* XAP: Extensible Authoring Publishing, obsoleted by XMP: Extensible Metadata Platform */
- { 0x0301, "Gamma"},
- { 0x0302, "ICCProfileDescriptor"},
- { 0x0303, "SRGBRenderingIntent"},
- { 0x0320, "ImageTitle"},
- { 0x5001, "ResolutionXUnit"},
- { 0x5002, "ResolutionYUnit"},
- { 0x5003, "ResolutionXLengthUnit"},
- { 0x5004, "ResolutionYLengthUnit"},
- { 0x5005, "PrintFlags"},
- { 0x5006, "PrintFlagsVersion"},
- { 0x5007, "PrintFlagsCrop"},
- { 0x5008, "PrintFlagsBleedWidth"},
- { 0x5009, "PrintFlagsBleedWidthScale"},
- { 0x500A, "HalftoneLPI"},
- { 0x500B, "HalftoneLPIUnit"},
- { 0x500C, "HalftoneDegree"},
- { 0x500D, "HalftoneShape"},
- { 0x500E, "HalftoneMisc"},
- { 0x500F, "HalftoneScreen"},
- { 0x5010, "JPEGQuality"},
- { 0x5011, "GridSize"},
- { 0x5012, "ThumbnailFormat"},
- { 0x5013, "ThumbnailWidth"},
- { 0x5014, "ThumbnailHeight"},
- { 0x5015, "ThumbnailColorDepth"},
- { 0x5016, "ThumbnailPlanes"},
- { 0x5017, "ThumbnailRawBytes"},
- { 0x5018, "ThumbnailSize"},
- { 0x5019, "ThumbnailCompressedSize"},
- { 0x501A, "ColorTransferFunction"},
- { 0x501B, "ThumbnailData"},
- { 0x5020, "ThumbnailImageWidth"},
- { 0x5021, "ThumbnailImageHeight"},
- { 0x5022, "ThumbnailBitsPerSample"},
- { 0x5023, "ThumbnailCompression"},
- { 0x5024, "ThumbnailPhotometricInterp"},
- { 0x5025, "ThumbnailImageDescription"},
- { 0x5026, "ThumbnailEquipMake"},
- { 0x5027, "ThumbnailEquipModel"},
- { 0x5028, "ThumbnailStripOffsets"},
- { 0x5029, "ThumbnailOrientation"},
- { 0x502A, "ThumbnailSamplesPerPixel"},
- { 0x502B, "ThumbnailRowsPerStrip"},
- { 0x502C, "ThumbnailStripBytesCount"},
- { 0x502D, "ThumbnailResolutionX"},
- { 0x502E, "ThumbnailResolutionY"},
- { 0x502F, "ThumbnailPlanarConfig"},
- { 0x5030, "ThumbnailResolutionUnit"},
- { 0x5031, "ThumbnailTransferFunction"},
- { 0x5032, "ThumbnailSoftwareUsed"},
- { 0x5033, "ThumbnailDateTime"},
- { 0x5034, "ThumbnailArtist"},
- { 0x5035, "ThumbnailWhitePoint"},
- { 0x5036, "ThumbnailPrimaryChromaticities"},
- { 0x5037, "ThumbnailYCbCrCoefficients"},
- { 0x5038, "ThumbnailYCbCrSubsampling"},
- { 0x5039, "ThumbnailYCbCrPositioning"},
- { 0x503A, "ThumbnailRefBlackWhite"},
- { 0x503B, "ThumbnailCopyRight"},
- { 0x5090, "LuminanceTable"},
- { 0x5091, "ChrominanceTable"},
- { 0x5100, "FrameDelay"},
- { 0x5101, "LoopCount"},
- { 0x5110, "PixelUnit"},
- { 0x5111, "PixelPerUnitX"},
- { 0x5112, "PixelPerUnitY"},
- { 0x5113, "PaletteHistogram"},
- { 0x1000, "RelatedImageFileFormat"},
- { 0x800D, "ImageID"},
- { 0x80E3, "Matteing"}, /* obsoleted by ExtraSamples */
- { 0x80E4, "DataType"}, /* obsoleted by SampleFormat */
- { 0x80E5, "ImageDepth"},
- { 0x80E6, "TileDepth"},
- { 0x828D, "CFARepeatPatternDim"},
- { 0x828E, "CFAPattern"},
- { 0x828F, "BatteryLevel"},
- { 0x8298, "Copyright"},
- { 0x829A, "ExposureTime"},
- { 0x829D, "FNumber"},
- { 0x83BB, "IPTC/NAA"},
- { 0x84E3, "IT8RasterPadding"},
- { 0x84E5, "IT8ColorTable"},
- { 0x8649, "ImageResourceInformation"}, /* PhotoShop */
- { 0x8769, "Exif_IFD_Pointer"},
- { 0x8773, "ICC_Profile"},
- { 0x8822, "ExposureProgram"},
- { 0x8824, "SpectralSensity"},
- { 0x8825, "GPS_IFD_Pointer"},
- { 0x8827, "ISOSpeedRatings"},
- { 0x8828, "OECF"},
- { 0x9000, "ExifVersion"},
- { 0x9003, "DateTimeOriginal"},
- { 0x9004, "DateTimeDigitized"},
- { 0x9101, "ComponentsConfiguration"},
- { 0x9102, "CompressedBitsPerPixel"},
- { 0x9201, "ShutterSpeedValue"},
- { 0x9202, "ApertureValue"},
- { 0x9203, "BrightnessValue"},
- { 0x9204, "ExposureBiasValue"},
- { 0x9205, "MaxApertureValue"},
- { 0x9206, "SubjectDistance"},
- { 0x9207, "MeteringMode"},
- { 0x9208, "LightSource"},
- { 0x9209, "Flash"},
- { 0x920A, "FocalLength"},
- { 0x920B, "FlashEnergy"}, /* 0xA20B in JPEG */
- { 0x920C, "SpatialFrequencyResponse"}, /* 0xA20C - - */
- { 0x920D, "Noise"},
- { 0x920E, "FocalPlaneXResolution"}, /* 0xA20E - - */
- { 0x920F, "FocalPlaneYResolution"}, /* 0xA20F - - */
- { 0x9210, "FocalPlaneResolutionUnit"}, /* 0xA210 - - */
- { 0x9211, "ImageNumber"},
- { 0x9212, "SecurityClassification"},
- { 0x9213, "ImageHistory"},
- { 0x9214, "SubjectLocation"}, /* 0xA214 - - */
- { 0x9215, "ExposureIndex"}, /* 0xA215 - - */
- { 0x9216, "TIFF/EPStandardID"},
- { 0x9217, "SensingMethod"}, /* 0xA217 - - */
- { 0x923F, "StoNits"},
- { 0x927C, "MakerNote"},
- { 0x9286, "UserComment"},
- { 0x9290, "SubSecTime"},
- { 0x9291, "SubSecTimeOriginal"},
- { 0x9292, "SubSecTimeDigitized"},
- { 0x935C, "ImageSourceData"}, /* "Adobe Photoshop Document Data Block": 8BIM... */
- { 0x9c9b, "Title" }, /* Win XP specific, Unicode */
- { 0x9c9c, "Comments" }, /* Win XP specific, Unicode */
- { 0x9c9d, "Author" }, /* Win XP specific, Unicode */
- { 0x9c9e, "Keywords" }, /* Win XP specific, Unicode */
- { 0x9c9f, "Subject" }, /* Win XP specific, Unicode, not to be confused with SubjectDistance and SubjectLocation */
- { 0xA000, "FlashPixVersion"},
- { 0xA001, "ColorSpace"},
- { 0xA002, "ExifImageWidth"},
- { 0xA003, "ExifImageLength"},
- { 0xA004, "RelatedSoundFile"},
- { 0xA005, "InteroperabilityOffset"},
- { 0xA20B, "FlashEnergy"}, /* 0x920B in TIFF/EP */
- { 0xA20C, "SpatialFrequencyResponse"}, /* 0x920C - - */
- { 0xA20D, "Noise"},
- { 0xA20E, "FocalPlaneXResolution"}, /* 0x920E - - */
- { 0xA20F, "FocalPlaneYResolution"}, /* 0x920F - - */
- { 0xA210, "FocalPlaneResolutionUnit"}, /* 0x9210 - - */
- { 0xA211, "ImageNumber"},
- { 0xA212, "SecurityClassification"},
- { 0xA213, "ImageHistory"},
- { 0xA214, "SubjectLocation"}, /* 0x9214 - - */
- { 0xA215, "ExposureIndex"}, /* 0x9215 - - */
- { 0xA216, "TIFF/EPStandardID"},
- { 0xA217, "SensingMethod"}, /* 0x9217 - - */
- { 0xA300, "FileSource"},
- { 0xA301, "SceneType"},
- { 0xA302, "CFAPattern"},
- { 0xA401, "CustomRendered"},
- { 0xA402, "ExposureMode"},
- { 0xA403, "WhiteBalance"},
- { 0xA404, "DigitalZoomRatio"},
- { 0xA405, "FocalLengthIn35mmFilm"},
- { 0xA406, "SceneCaptureType"},
- { 0xA407, "GainControl"},
- { 0xA408, "Contrast"},
- { 0xA409, "Saturation"},
- { 0xA40A, "Sharpness"},
- { 0xA40B, "DeviceSettingDescription"},
- { 0xA40C, "SubjectDistanceRange"},
- { 0xA420, "ImageUniqueID"},
- TAG_TABLE_END
- } ;
- static tag_info_array tag_table_GPS = {
- { 0x0000, "GPSVersion"},
- { 0x0001, "GPSLatitudeRef"},
- { 0x0002, "GPSLatitude"},
- { 0x0003, "GPSLongitudeRef"},
- { 0x0004, "GPSLongitude"},
- { 0x0005, "GPSAltitudeRef"},
- { 0x0006, "GPSAltitude"},
- { 0x0007, "GPSTimeStamp"},
- { 0x0008, "GPSSatellites"},
- { 0x0009, "GPSStatus"},
- { 0x000A, "GPSMeasureMode"},
- { 0x000B, "GPSDOP"},
- { 0x000C, "GPSSpeedRef"},
- { 0x000D, "GPSSpeed"},
- { 0x000E, "GPSTrackRef"},
- { 0x000F, "GPSTrack"},
- { 0x0010, "GPSImgDirectionRef"},
- { 0x0011, "GPSImgDirection"},
- { 0x0012, "GPSMapDatum"},
- { 0x0013, "GPSDestLatitudeRef"},
- { 0x0014, "GPSDestLatitude"},
- { 0x0015, "GPSDestLongitudeRef"},
- { 0x0016, "GPSDestLongitude"},
- { 0x0017, "GPSDestBearingRef"},
- { 0x0018, "GPSDestBearing"},
- { 0x0019, "GPSDestDistanceRef"},
- { 0x001A, "GPSDestDistance"},
- { 0x001B, "GPSProcessingMode"},
- { 0x001C, "GPSAreaInformation"},
- { 0x001D, "GPSDateStamp"},
- { 0x001E, "GPSDifferential"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_IOP = {
- { 0x0001, "InterOperabilityIndex"}, /* should be 'R98' or 'THM' */
- { 0x0002, "InterOperabilityVersion"},
- { 0x1000, "RelatedFileFormat"},
- { 0x1001, "RelatedImageWidth"},
- { 0x1002, "RelatedImageHeight"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_CANON = {
- { 0x0001, "ModeArray"}, /* guess */
- { 0x0004, "ImageInfo"}, /* guess */
- { 0x0006, "ImageType"},
- { 0x0007, "FirmwareVersion"},
- { 0x0008, "ImageNumber"},
- { 0x0009, "OwnerName"},
- { 0x000C, "Camera"},
- { 0x000F, "CustomFunctions"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_CASIO = {
- { 0x0001, "RecordingMode"},
- { 0x0002, "Quality"},
- { 0x0003, "FocusingMode"},
- { 0x0004, "FlashMode"},
- { 0x0005, "FlashIntensity"},
- { 0x0006, "ObjectDistance"},
- { 0x0007, "WhiteBalance"},
- { 0x000A, "DigitalZoom"},
- { 0x000B, "Sharpness"},
- { 0x000C, "Contrast"},
- { 0x000D, "Saturation"},
- { 0x0014, "CCDSensitivity"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_FUJI = {
- { 0x0000, "Version"},
- { 0x1000, "Quality"},
- { 0x1001, "Sharpness"},
- { 0x1002, "WhiteBalance"},
- { 0x1003, "Color"},
- { 0x1004, "Tone"},
- { 0x1010, "FlashMode"},
- { 0x1011, "FlashStrength"},
- { 0x1020, "Macro"},
- { 0x1021, "FocusMode"},
- { 0x1030, "SlowSync"},
- { 0x1031, "PictureMode"},
- { 0x1100, "ContTake"},
- { 0x1300, "BlurWarning"},
- { 0x1301, "FocusWarning"},
- { 0x1302, "AEWarning "},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_NIKON = {
- { 0x0003, "Quality"},
- { 0x0004, "ColorMode"},
- { 0x0005, "ImageAdjustment"},
- { 0x0006, "CCDSensitivity"},
- { 0x0007, "WhiteBalance"},
- { 0x0008, "Focus"},
- { 0x000a, "DigitalZoom"},
- { 0x000b, "Converter"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_NIKON_990 = {
- { 0x0001, "Version"},
- { 0x0002, "ISOSetting"},
- { 0x0003, "ColorMode"},
- { 0x0004, "Quality"},
- { 0x0005, "WhiteBalance"},
- { 0x0006, "ImageSharpening"},
- { 0x0007, "FocusMode"},
- { 0x0008, "FlashSetting"},
- { 0x000F, "ISOSelection"},
- { 0x0080, "ImageAdjustment"},
- { 0x0082, "AuxiliaryLens"},
- { 0x0085, "ManualFocusDistance"},
- { 0x0086, "DigitalZoom"},
- { 0x0088, "AFFocusPosition"},
- { 0x0010, "DataDump"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_OLYMPUS = {
- { 0x0200, "SpecialMode"},
- { 0x0201, "JPEGQuality"},
- { 0x0202, "Macro"},
- { 0x0204, "DigitalZoom"},
- { 0x0207, "SoftwareRelease"},
- { 0x0208, "PictureInfo"},
- { 0x0209, "CameraId"},
- { 0x0F00, "DataDump"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_SAMSUNG = {
- { 0x0001, "Version"},
- { 0x0021, "PictureWizard"},
- { 0x0030, "LocalLocationName"},
- { 0x0031, "LocationName"},
- { 0x0035, "Preview"},
- { 0x0043, "CameraTemperature"},
- { 0xa001, "FirmwareName"},
- { 0xa003, "LensType"},
- { 0xa004, "LensFirmware"},
- { 0xa010, "SensorAreas"},
- { 0xa011, "ColorSpace"},
- { 0xa012, "SmartRange"},
- { 0xa013, "ExposureBiasValue"},
- { 0xa014, "ISO"},
- { 0xa018, "ExposureTime"},
- { 0xa019, "FNumber"},
- { 0xa01a, "FocalLengthIn35mmFormat"},
- { 0xa020, "EncryptionKey"},
- { 0xa021, "WB_RGGBLevelsUncorrected"},
- { 0xa022, "WB_RGGBLevelsAuto"},
- { 0xa023, "WB_RGGBLevelsIlluminator1"},
- { 0xa024, "WB_RGGBLevelsIlluminator2"},
- { 0xa028, "WB_RGGBLevelsBlack"},
- { 0xa030, "ColorMatrix"},
- { 0xa031, "ColorMatrixSRGB"},
- { 0xa032, "ColorMatrixAdobeRGB"},
- { 0xa040, "ToneCurve1"},
- { 0xa041, "ToneCurve2"},
- { 0xa042, "ToneCurve3"},
- { 0xa043, "ToneCurve4"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_PANASONIC = {
- { 0x0001, "Quality"},
- { 0x0002, "FirmwareVersion"},
- { 0x0003, "WhiteBalance"},
- { 0x0007, "FocusMode"},
- { 0x000f, "AFMode"},
- { 0x001a, "ImageStabilization"},
- { 0x001c, "Macro"},
- { 0x001f, "ShootingMode"},
- { 0x0020, "Audio"},
- { 0x0021, "DataDump"},
- { 0x0023, "WhiteBalanceBias"},
- { 0x0024, "FlashBias"},
- { 0x0025, "InternalSerialNumber"},
- { 0x0026, "ExifVersion"},
- { 0x0028, "ColorEffect"},
- { 0x0029, "TimeSincePowerOn"},
- { 0x002a, "BurstMode"},
- { 0x002b, "SequenceNumber"},
- { 0x002c, "Contrast"},
- { 0x002d, "NoiseReduction"},
- { 0x002e, "SelfTimer"},
- { 0x0030, "Rotation"},
- { 0x0031, "AFAssistLamp"},
- { 0x0032, "ColorMode"},
- { 0x0033, "BabyAge1"},
- { 0x0034, "OpticalZoomMode"},
- { 0x0035, "ConversionLens"},
- { 0x0036, "TravelDay"},
- { 0x0039, "Contrast"},
- { 0x003a, "WorldTimeLocation"},
- { 0x003b, "TextStamp1"},
- { 0x003c, "ProgramISO"},
- { 0x003d, "AdvancedSceneType"},
- { 0x003e, "TextStamp2"},
- { 0x003f, "FacesDetected"},
- { 0x0040, "Saturation"},
- { 0x0041, "Sharpness"},
- { 0x0042, "FilmMode"},
- { 0x0044, "ColorTempKelvin"},
- { 0x0045, "BracketSettings"},
- { 0x0046, "WBAdjustAB"},
- { 0x0047, "WBAdjustGM"},
- { 0x0048, "FlashCurtain"},
- { 0x0049, "LongShutterNoiseReduction"},
- { 0x004b, "ImageWidth"},
- { 0x004c, "ImageHeight"},
- { 0x004d, "AFPointPosition"},
- { 0x004e, "FaceDetInfo"},
- { 0x0051, "LensType"},
- { 0x0052, "LensSerialNumber"},
- { 0x0053, "AccessoryType"},
- { 0x0054, "AccessorySerialNumber"},
- { 0x0059, "Transform1"},
- { 0x005d, "IntelligentExposure"},
- { 0x0060, "LensFirmwareVersion"},
- { 0x0061, "FaceRecInfo"},
- { 0x0062, "FlashWarning"},
- { 0x0065, "Title"},
- { 0x0066, "BabyName"},
- { 0x0067, "Location"},
- { 0x0069, "Country"},
- { 0x006b, "State"},
- { 0x006d, "City"},
- { 0x006f, "Landmark"},
- { 0x0070, "IntelligentResolution"},
- { 0x0077, "BurstSheed"},
- { 0x0079, "IntelligentDRange"},
- { 0x007c, "ClearRetouch"},
- { 0x0080, "City2"},
- { 0x0086, "ManometerPressure"},
- { 0x0089, "PhotoStyle"},
- { 0x008a, "ShadingCompensation"},
- { 0x008c, "AccelerometerZ"},
- { 0x008d, "AccelerometerX"},
- { 0x008e, "AccelerometerY"},
- { 0x008f, "CameraOrientation"},
- { 0x0090, "RollAngle"},
- { 0x0091, "PitchAngle"},
- { 0x0093, "SweepPanoramaDirection"},
- { 0x0094, "PanoramaFieldOfView"},
- { 0x0096, "TimerRecording"},
- { 0x009d, "InternalNDFilter"},
- { 0x009e, "HDR"},
- { 0x009f, "ShutterType"},
- { 0x00a3, "ClearRetouchValue"},
- { 0x00ab, "TouchAE"},
- { 0x0e00, "PrintIM"},
- { 0x8000, "MakerNoteVersion"},
- { 0x8001, "SceneMode"},
- { 0x8004, "WBRedLevel"},
- { 0x8005, "WBGreenLevel"},
- { 0x8006, "WBBlueLevel"},
- { 0x8007, "FlashFired"},
- { 0x8008, "TextStamp3"},
- { 0x8009, "TextStamp4"},
- { 0x8010, "BabyAge2"},
- { 0x8012, "Transform2"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_DJI = {
- { 0x0001, "Make"},
- { 0x0003, "SpeedX"},
- { 0x0004, "SpeedY"},
- { 0x0005, "SpeedZ"},
- { 0x0006, "Pitch"},
- { 0x0007, "Yaw"},
- { 0x0008, "Roll"},
- { 0x0009, "CameraPitch"},
- { 0x000a, "CameraYaw"},
- { 0x000b, "CameraRoll"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_SONY = {
- { 0x0102, "Quality"},
- { 0x0104, "FlashExposureComp"},
- { 0x0105, "Teleconverter"},
- { 0x0112, "WhiteBalanceFineTune"},
- { 0x0114, "CameraSettings"},
- { 0x0115, "WhiteBalance"},
- { 0x0116, "ExtraInfo"},
- { 0x0e00, "PrintIM"},
- { 0x1000, "MultiBurstMode"},
- { 0x1001, "MultiBurstImageWidth"},
- { 0x1002, "MultiBurstImageHeight"},
- { 0x1003, "Panorama"},
- { 0x2001, "PreviewImage"},
- { 0x2002, "Rating"},
- { 0x2004, "Contrast"},
- { 0x2005, "Saturation"},
- { 0x2006, "Sharpness"},
- { 0x2007, "Brightness"},
- { 0x2008, "LongExposureNoiseReduction"},
- { 0x2009, "HighISONoiseReduction"},
- { 0x200a, "AutoHDR"},
- { 0x3000, "ShotInfo"},
- { 0xb000, "FileFormat"},
- { 0xb001, "SonyModelID"},
- { 0xb020, "ColorReproduction"},
- { 0xb021, "ColorTemperature"},
- { 0xb022, "ColorCompensationFilter"},
- { 0xb023, "SceneMode"},
- { 0xb024, "ZoneMatching"},
- { 0xb025, "DynamicRangeOptimizer"},
- { 0xb026, "ImageStabilization"},
- { 0xb027, "LensID"},
- { 0xb028, "MinoltaMakerNote"},
- { 0xb029, "ColorMode"},
- { 0xb02b, "FullImageSize"},
- { 0xb02c, "PreviewImageSize"},
- { 0xb040, "Macro"},
- { 0xb041, "ExposureMode"},
- { 0xb042, "FocusMode"},
- { 0xb043, "AFMode"},
- { 0xb044, "AFIlluminator"},
- { 0xb047, "JPEGQuality"},
- { 0xb048, "FlashLevel"},
- { 0xb049, "ReleaseMode"},
- { 0xb04a, "SequenceNumber"},
- { 0xb04b, "AntiBlur"},
- { 0xb04e, "FocusMode"},
- { 0xb04f, "DynamicRangeOptimizer"},
- { 0xb050, "HighISONoiseReduction2"},
- { 0xb052, "IntelligentAuto"},
- { 0xb054, "WhiteBalance2"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_PENTAX = {
- { 0x0000, "Version"},
- { 0x0001, "Mode"},
- { 0x0002, "PreviewResolution"},
- { 0x0003, "PreviewLength"},
- { 0x0004, "PreviewOffset"},
- { 0x0005, "ModelID"},
- { 0x0006, "Date"},
- { 0x0007, "Time"},
- { 0x0008, "Quality"},
- { 0x0009, "Size"},
- { 0x000c, "Flash"},
- { 0x000d, "Focus"},
- { 0x000e, "AFPoint"},
- { 0x000f, "AFPointInFocus"},
- { 0x0012, "ExposureTime"},
- { 0x0013, "FNumber"},
- { 0x0014, "ISO"},
- { 0x0016, "ExposureCompensation"},
- { 0x0017, "MeteringMode"},
- { 0x0018, "AutoBracketing"},
- { 0x0019, "WhiteBalance"},
- { 0x001a, "WhiteBalanceMode"},
- { 0x001b, "BlueBalance"},
- { 0x001c, "RedBalance"},
- { 0x001d, "FocalLength"},
- { 0x001e, "DigitalZoom"},
- { 0x001f, "Saturation"},
- { 0x0020, "Contrast"},
- { 0x0021, "Sharpness"},
- { 0x0022, "Location"},
- { 0x0023, "Hometown"},
- { 0x0024, "Destination"},
- { 0x0025, "HometownDST"},
- { 0x0026, "DestinationDST"},
- { 0x0027, "DSPFirmwareVersion"},
- { 0x0028, "CPUFirmwareVersion"},
- { 0x0029, "FrameNumber"},
- { 0x002d, "EffectiveLV"},
- { 0x0032, "ImageProcessing"},
- { 0x0033, "PictureMode"},
- { 0x0034, "DriveMode"},
- { 0x0037, "ColorSpace"},
- { 0x0038, "ImageAreaOffset"},
- { 0x0039, "RawImageSize"},
- { 0x003e, "PreviewImageBorders"},
- { 0x003f, "LensType"},
- { 0x0040, "SensitivityAdjust"},
- { 0x0041, "DigitalFilter"},
- { 0x0047, "Temperature"},
- { 0x0048, "AELock"},
- { 0x0049, "NoiseReduction"},
- { 0x004d, "FlashExposureCompensation"},
- { 0x004f, "ImageTone"},
- { 0x0050, "ColorTemperature"},
- { 0x005c, "ShakeReduction"},
- { 0x005d, "ShutterCount"},
- { 0x0069, "DynamicRangeExpansion"},
- { 0x0071, "HighISONoiseReduction"},
- { 0x0072, "AFAdjustment"},
- { 0x0200, "BlackPoint"},
- { 0x0201, "WhitePoint"},
- { 0x0205, "ShotInfo"},
- { 0x0206, "AEInfo"},
- { 0x0207, "LensInfo"},
- { 0x0208, "FlashInfo"},
- { 0x0209, "AEMeteringSegments"},
- { 0x020a, "FlashADump"},
- { 0x020b, "FlashBDump"},
- { 0x020d, "WB_RGGBLevelsDaylight"},
- { 0x020e, "WB_RGGBLevelsShade"},
- { 0x020f, "WB_RGGBLevelsCloudy"},
- { 0x0210, "WB_RGGBLevelsTungsten"},
- { 0x0211, "WB_RGGBLevelsFluorescentD"},
- { 0x0212, "WB_RGGBLevelsFluorescentN"},
- { 0x0213, "WB_RGGBLevelsFluorescentW"},
- { 0x0214, "WB_RGGBLevelsFlash"},
- { 0x0215, "CameraInfo"},
- { 0x0216, "BatteryInfo"},
- { 0x021f, "AFInfo"},
- { 0x0222, "ColorInfo"},
- { 0x0229, "SerialNumber"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_MINOLTA = {
- { 0x0000, "Version"},
- { 0x0001, "CameraSettingsStdOld"},
- { 0x0003, "CameraSettingsStdNew"},
- { 0x0004, "CameraSettings7D"},
- { 0x0018, "ImageStabilizationData"},
- { 0x0020, "WBInfoA100"},
- { 0x0040, "CompressedImageSize"},
- { 0x0081, "Thumbnail"},
- { 0x0088, "ThumbnailOffset"},
- { 0x0089, "ThumbnailLength"},
- { 0x0100, "SceneMode"},
- { 0x0101, "ColorMode"},
- { 0x0102, "Quality"},
- { 0x0104, "FlashExposureComp"},
- { 0x0105, "Teleconverter"},
- { 0x0107, "ImageStabilization"},
- { 0x0109, "RawAndJpgRecording"},
- { 0x010a, "ZoneMatching"},
- { 0x010b, "ColorTemperature"},
- { 0x010c, "LensID"},
- { 0x0111, "ColorCompensationFilter"},
- { 0x0112, "WhiteBalanceFineTune"},
- { 0x0113, "ImageStabilizationA100"},
- { 0x0114, "CameraSettings5D"},
- { 0x0115, "WhiteBalance"},
- { 0x0e00, "PrintIM"},
- { 0x0f00, "CameraSettingsZ1"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_SIGMA = {
- { 0x0002, "SerialNumber"},
- { 0x0003, "DriveMode"},
- { 0x0004, "ResolutionMode"},
- { 0x0005, "AutofocusMode"},
- { 0x0006, "FocusSetting"},
- { 0x0007, "WhiteBalance"},
- { 0x0008, "ExposureMode"},
- { 0x0009, "MeteringMode"},
- { 0x000a, "LensRange"},
- { 0x000b, "ColorSpace"},
- { 0x000c, "Exposure"},
- { 0x000d, "Contrast"},
- { 0x000e, "Shadow"},
- { 0x000f, "Highlight"},
- { 0x0010, "Saturation"},
- { 0x0011, "Sharpness"},
- { 0x0012, "FillLight"},
- { 0x0014, "ColorAdjustment"},
- { 0x0015, "AdjustmentMode"},
- { 0x0016, "Quality"},
- { 0x0017, "Firmware"},
- { 0x0018, "Software"},
- { 0x0019, "AutoBracket"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_KYOCERA = {
- { 0x0001, "FormatThumbnail"},
- { 0x0E00, "PrintImageMatchingInfo"},
- TAG_TABLE_END
- };
- static tag_info_array tag_table_VND_RICOH = {
- { 0x0001, "MakerNoteDataType"},
- { 0x0002, "Version"},
- { 0x0E00, "PrintImageMatchingInfo"},
- { 0x2001, "RicohCameraInfoMakerNoteSubIFD"},
- TAG_TABLE_END
- };
- typedef enum mn_byte_order_t {
- MN_ORDER_INTEL = 0,
- MN_ORDER_MOTOROLA = 1,
- MN_ORDER_NORMAL
- } mn_byte_order_t;
- typedef enum mn_offset_mode_t {
- MN_OFFSET_NORMAL,
- MN_OFFSET_MAKER
- } mn_offset_mode_t;
- typedef struct {
- tag_table_type tag_table;
- char * make;
- char * id_string;
- int id_string_len;
- int offset;
- mn_byte_order_t byte_order;
- mn_offset_mode_t offset_mode;
- } maker_note_type;
- /* Remember to update PHP_MINFO if updated */
- static const maker_note_type maker_note_array[] = {
- { tag_table_VND_CANON, "Canon", NULL, 0, 0, MN_ORDER_INTEL, MN_OFFSET_NORMAL},
- { tag_table_VND_CASIO, "CASIO", NULL, 0, 0, MN_ORDER_MOTOROLA, MN_OFFSET_NORMAL},
- { tag_table_VND_FUJI, "FUJIFILM", "FUJIFILM\x0C\x00\x00\x00", 12, 12, MN_ORDER_INTEL, MN_OFFSET_MAKER},
- { tag_table_VND_NIKON, "NIKON", "Nikon\x00\x01\x00", 8, 8, MN_ORDER_NORMAL, MN_OFFSET_NORMAL},
- { tag_table_VND_NIKON_990, "NIKON", NULL, 0, 0, MN_ORDER_NORMAL, MN_OFFSET_NORMAL},
- { tag_table_VND_OLYMPUS, "OLYMPUS OPTICAL CO.,LTD", "OLYMP\x00\x01\x00", 8, 8, MN_ORDER_NORMAL, MN_OFFSET_NORMAL},
- { tag_table_VND_SAMSUNG, "SAMSUNG", NULL, 0, 0, MN_ORDER_NORMAL, MN_OFFSET_NORMAL},
- { tag_table_VND_PANASONIC, "Panasonic", "Panasonic\x00\x00\x00", 12, 12, MN_ORDER_NORMAL, MN_OFFSET_NORMAL},
- { tag_table_VND_DJI, "DJI", NULL, 0, 0, MN_ORDER_NORMAL, MN_OFFSET_NORMAL},
- { tag_table_VND_SONY, "SONY", "SONY DSC \x00\x00\x00", 12, 12, MN_ORDER_NORMAL, MN_OFFSET_NORMAL},
- { tag_table_VND_SONY, "SONY", NULL, 0, 0, MN_ORDER_NORMAL, MN_OFFSET_NORMAL},
- { tag_table_VND_PENTAX, "PENTAX", "AOC\x00", 6, 6, MN_ORDER_NORMAL, MN_OFFSET_NORMAL},
- { tag_table_VND_MINOLTA, "Minolta, KONICA MINOLTA", NULL, 0, 0, MN_ORDER_NORMAL, MN_OFFSET_NORMAL},
- { tag_table_VND_SIGMA, "SIGMA, FOVEON", "SIGMA\x00\x00\x00", 10, 10, MN_ORDER_NORMAL, MN_OFFSET_NORMAL},
- { tag_table_VND_SIGMA, "SIGMA, FOVEON", "FOVEON\x00\x00\x00", 10, 10, MN_ORDER_NORMAL, MN_OFFSET_NORMAL},
- { tag_table_VND_KYOCERA, "KYOCERA, CONTAX", "KYOCERA \x00\x00\x00", 22, 22, MN_ORDER_NORMAL, MN_OFFSET_MAKER},
- { tag_table_VND_RICOH, "RICOH", "Ricoh", 5, 5, MN_ORDER_MOTOROLA, MN_OFFSET_NORMAL},
- { tag_table_VND_RICOH, "RICOH", "RICOH", 5, 5, MN_ORDER_MOTOROLA, MN_OFFSET_NORMAL},
- /* These re-uses existing formats */
- { tag_table_VND_OLYMPUS, "AGFA", "AGFA \x00\x01", 8, 8, MN_ORDER_NORMAL, MN_OFFSET_NORMAL},
- { tag_table_VND_OLYMPUS, "EPSON", "EPSON\x00\x01\x00", 8, 8, MN_ORDER_NORMAL, MN_OFFSET_NORMAL}
- };
- /* }}} */
- static HashTable *exif_make_tag_ht(tag_info_type *tag_table)
- {
- HashTable *ht = malloc(sizeof(HashTable));
- zend_hash_init(ht, 0, NULL, NULL, 1);
- while (tag_table->Tag != TAG_END_OF_LIST) {
- if (!zend_hash_index_add_ptr(ht, tag_table->Tag, tag_table->Desc)) {
- zend_error(E_CORE_ERROR, "Duplicate tag %x", tag_table->Tag);
- }
- tag_table++;
- }
- return ht;
- }
- static void exif_tag_ht_dtor(zval *zv)
- {
- HashTable *ht = Z_PTR_P(zv);
- zend_hash_destroy(ht);
- free(ht);
- }
- static HashTable *exif_get_tag_ht(tag_info_type *tag_table)
- {
- HashTable *ht;
- if (!EXIF_G(tag_table_cache)) {
- EXIF_G(tag_table_cache) = malloc(sizeof(HashTable));
- zend_hash_init(EXIF_G(tag_table_cache), 0, NULL, exif_tag_ht_dtor, 1);
- }
- ht = zend_hash_index_find_ptr(EXIF_G(tag_table_cache), (uintptr_t) tag_table);
- if (ht) {
- return ht;
- }
- ht = exif_make_tag_ht(tag_table);
- zend_hash_index_add_new_ptr(EXIF_G(tag_table_cache), (uintptr_t) tag_table, ht);
- return ht;
- }
- /* {{{ exif_get_tagname
- Get headername for tag_num or NULL if not defined */
- static char *exif_get_tagname(int tag_num, tag_table_type tag_table)
- {
- return zend_hash_index_find_ptr(exif_get_tag_ht(tag_table), tag_num);
- }
- /* }}} */
- static char *exif_get_tagname_debug(int tag_num, tag_table_type tag_table)
- {
- char *desc = zend_hash_index_find_ptr(exif_get_tag_ht(tag_table), tag_num);
- if (desc) {
- return desc;
- }
- return "UndefinedTag";
- }
- static char *exif_get_tagname_key(int tag_num, char *buf, size_t buf_size, tag_table_type tag_table)
- {
- char *desc = zend_hash_index_find_ptr(exif_get_tag_ht(tag_table), tag_num);
- if (desc) {
- return desc;
- }
- snprintf(buf, buf_size, "UndefinedTag:0x%04X", tag_num);
- return buf;
- }
- /* {{{ exif_char_dump
- * Do not use! This is a debug function... */
- #ifdef EXIF_DEBUG
- static unsigned char* exif_char_dump(unsigned char * addr, int len, int offset)
- {
- static unsigned char buf[4096+1];
- static unsigned char tmp[20];
- int c, i, p=0, n = 5+31;
- p += slprintf(buf+p, sizeof(buf)-p, "\nDump Len: %08X (%d)", len, len);
- if (len) {
- for(i=0; i<len+15 && p+n<=sizeof(buf); i++) {
- if (i%16==0) {
- p += slprintf(buf+p, sizeof(buf)-p, "\n%08X: ", i+offset);
- }
- if (i<len) {
- c = *addr++;
- p += slprintf(buf+p, sizeof(buf)-p, "%02X ", c);
- tmp[i%16] = c>=32 ? c : '.';
- tmp[(i%16)+1] = '\0';
- } else {
- p += slprintf(buf+p, sizeof(buf)-p, " ");
- }
- if (i%16==15) {
- p += slprintf(buf+p, sizeof(buf)-p, " %s", tmp);
- if (i>=len) {
- break;
- }
- }
- }
- }
- buf[sizeof(buf)-1] = '\0';
- return buf;
- }
- #endif
- /* }}} */
- /* {{{ php_jpg_get16
- Get 16 bits motorola order (always) for jpeg header stuff.
- */
- static int php_jpg_get16(void *value)
- {
- return (((uchar *)value)[0] << 8) | ((uchar *)value)[1];
- }
- /* }}} */
- /* {{{ php_ifd_get16u
- * Convert a 16 bit unsigned value from file's native byte order */
- static int php_ifd_get16u(void *value, int motorola_intel)
- {
- if (motorola_intel) {
- return (((uchar *)value)[0] << 8) | ((uchar *)value)[1];
- } else {
- return (((uchar *)value)[1] << 8) | ((uchar *)value)[0];
- }
- }
- /* }}} */
- /* {{{ php_ifd_get16s
- * Convert a 16 bit signed value from file's native byte order */
- static signed short php_ifd_get16s(void *value, int motorola_intel)
- {
- return (signed short)php_ifd_get16u(value, motorola_intel);
- }
- /* }}} */
- /* {{{ php_ifd_get32u
- * Convert a 32 bit unsigned value from file's native byte order */
- static unsigned php_ifd_get32u(void *void_value, int motorola_intel)
- {
- uchar *value = (uchar *) void_value;
- if (motorola_intel) {
- return ((unsigned)value[0] << 24)
- | ((unsigned)value[1] << 16)
- | ((unsigned)value[2] << 8 )
- | ((unsigned)value[3] );
- } else {
- return ((unsigned)value[3] << 24)
- | ((unsigned)value[2] << 16)
- | ((unsigned)value[1] << 8 )
- | ((unsigned)value[0] );
- }
- }
- /* }}} */
- /* {{{ php_ifd_get64u
- * Convert a 64 bit unsigned value from file's native byte order */
- static uint64_t php_ifd_get64u(void *void_value, int motorola_intel)
- {
- uchar *value = (uchar *) void_value;
- if (motorola_intel) {
- return ((uint64_t)value[0] << 56)
- | ((uint64_t)value[1] << 48)
- | ((uint64_t)value[2] << 40)
- | ((uint64_t)value[3] << 32)
- | ((uint64_t)value[4] << 24)
- | ((uint64_t)value[5] << 16)
- | ((uint64_t)value[6] << 8 )
- | ((uint64_t)value[7] );
- } else {
- return ((uint64_t)value[7] << 56)
- | ((uint64_t)value[6] << 48)
- | ((uint64_t)value[5] << 40)
- | ((uint64_t)value[4] << 32)
- | ((uint64_t)value[3] << 24)
- | ((uint64_t)value[2] << 16)
- | ((uint64_t)value[1] << 8 )
- | ((uint64_t)value[0] );
- }
- }
- /* }}} */
- /* {{{ php_ifd_get32u
- * Convert a 32 bit signed value from file's native byte order */
- static unsigned php_ifd_get32s(void *value, int motorola_intel)
- {
- return (int) php_ifd_get32u(value, motorola_intel);
- }
- /* }}} */
- /* {{{ php_ifd_set16u
- * Write 16 bit unsigned value to data */
- static void php_ifd_set16u(char *data, unsigned int value, int motorola_intel)
- {
- if (motorola_intel) {
- data[0] = (value & 0xFF00) >> 8;
- data[1] = (value & 0x00FF);
- } else {
- data[1] = (value & 0xFF00) >> 8;
- data[0] = (value & 0x00FF);
- }
- }
- /* }}} */
- /* {{{ php_ifd_set32u
- * Convert a 32 bit unsigned value from file's native byte order */
- static void php_ifd_set32u(char *data, size_t value, int motorola_intel)
- {
- if (motorola_intel) {
- data[0] = (value & 0xFF000000) >> 24;
- dat…
Large files files are truncated, but you can click here to view the full file