exiftool_vendored 10.65.0 → 11.41.0

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of exiftool_vendored might be problematic. Click here for more details.

Files changed (205) hide show
  1. checksums.yaml +4 -4
  2. data/bin/Changes +818 -19
  3. data/bin/MANIFEST +38 -0
  4. data/bin/META.json +1 -1
  5. data/bin/META.yml +1 -1
  6. data/bin/README +48 -44
  7. data/bin/arg_files/exif2xmp.args +4 -1
  8. data/bin/arg_files/gps2xmp.args +4 -1
  9. data/bin/arg_files/iptcCore.args +8 -0
  10. data/bin/arg_files/xmp2exif.args +4 -1
  11. data/bin/arg_files/xmp2gps.args +4 -1
  12. data/bin/config_files/dji.config +131 -0
  13. data/bin/config_files/example.config +6 -2
  14. data/bin/config_files/gps2utm.config +256 -256
  15. data/bin/config_files/nksc.config +146 -0
  16. data/bin/config_files/picasa_faces.config +382 -382
  17. data/bin/exiftool +688 -408
  18. data/bin/fmt_files/gpx.fmt +10 -6
  19. data/bin/fmt_files/gpx_wpt.fmt +10 -6
  20. data/bin/fmt_files/kml.fmt +8 -5
  21. data/bin/lib/File/RandomAccess.pm +48 -8
  22. data/bin/lib/File/RandomAccess.pod +21 -2
  23. data/bin/lib/Image/ExifTool.pm +645 -256
  24. data/bin/lib/Image/ExifTool.pod +219 -164
  25. data/bin/lib/Image/ExifTool/AES.pm +1 -1
  26. data/bin/lib/Image/ExifTool/AFCP.pm +3 -8
  27. data/bin/lib/Image/ExifTool/AIFF.pm +12 -4
  28. data/bin/lib/Image/ExifTool/APE.pm +1 -1
  29. data/bin/lib/Image/ExifTool/APP12.pm +1 -1
  30. data/bin/lib/Image/ExifTool/ASF.pm +19 -6
  31. data/bin/lib/Image/ExifTool/Apple.pm +13 -5
  32. data/bin/lib/Image/ExifTool/Audible.pm +1 -1
  33. data/bin/lib/Image/ExifTool/BMP.pm +1 -1
  34. data/bin/lib/Image/ExifTool/BPG.pm +17 -15
  35. data/bin/lib/Image/ExifTool/BZZ.pm +1 -1
  36. data/bin/lib/Image/ExifTool/BigTIFF.pm +30 -15
  37. data/bin/lib/Image/ExifTool/BuildTagLookup.pm +103 -52
  38. data/bin/lib/Image/ExifTool/Canon.pm +684 -112
  39. data/bin/lib/Image/ExifTool/CanonCustom.pm +119 -9
  40. data/bin/lib/Image/ExifTool/CanonRaw.pm +1 -1
  41. data/bin/lib/Image/ExifTool/CanonVRD.pm +13 -26
  42. data/bin/lib/Image/ExifTool/CaptureOne.pm +1 -1
  43. data/bin/lib/Image/ExifTool/Casio.pm +1 -1
  44. data/bin/lib/Image/ExifTool/Charset.pm +1 -1
  45. data/bin/lib/Image/ExifTool/DICOM.pm +12 -5
  46. data/bin/lib/Image/ExifTool/DJI.pm +51 -3
  47. data/bin/lib/Image/ExifTool/DNG.pm +15 -8
  48. data/bin/lib/Image/ExifTool/DPX.pm +1 -1
  49. data/bin/lib/Image/ExifTool/DV.pm +1 -1
  50. data/bin/lib/Image/ExifTool/DarwinCore.pm +63 -23
  51. data/bin/lib/Image/ExifTool/DjVu.pm +4 -2
  52. data/bin/lib/Image/ExifTool/EXE.pm +30 -6
  53. data/bin/lib/Image/ExifTool/Exif.pm +351 -109
  54. data/bin/lib/Image/ExifTool/FITS.pm +148 -0
  55. data/bin/lib/Image/ExifTool/FLAC.pm +2 -2
  56. data/bin/lib/Image/ExifTool/FLIF.pm +1 -1
  57. data/bin/lib/Image/ExifTool/FLIR.pm +109 -13
  58. data/bin/lib/Image/ExifTool/Fixup.pm +1 -1
  59. data/bin/lib/Image/ExifTool/Flash.pm +3 -3
  60. data/bin/lib/Image/ExifTool/FlashPix.pm +433 -9
  61. data/bin/lib/Image/ExifTool/Font.pm +2 -2
  62. data/bin/lib/Image/ExifTool/FotoStation.pm +1 -1
  63. data/bin/lib/Image/ExifTool/FujiFilm.pm +336 -16
  64. data/bin/lib/Image/ExifTool/GE.pm +1 -1
  65. data/bin/lib/Image/ExifTool/GIF.pm +5 -7
  66. data/bin/lib/Image/ExifTool/GIMP.pm +39 -3
  67. data/bin/lib/Image/ExifTool/GPS.pm +48 -22
  68. data/bin/lib/Image/ExifTool/GeoTiff.pm +23 -23
  69. data/bin/lib/Image/ExifTool/Geotag.pm +80 -45
  70. data/bin/lib/Image/ExifTool/GoPro.pm +709 -0
  71. data/bin/lib/Image/ExifTool/H264.pm +40 -18
  72. data/bin/lib/Image/ExifTool/HP.pm +1 -1
  73. data/bin/lib/Image/ExifTool/HTML.pm +19 -12
  74. data/bin/lib/Image/ExifTool/HtmlDump.pm +37 -26
  75. data/bin/lib/Image/ExifTool/ICC_Profile.pm +297 -23
  76. data/bin/lib/Image/ExifTool/ID3.pm +12 -7
  77. data/bin/lib/Image/ExifTool/IPTC.pm +48 -19
  78. data/bin/lib/Image/ExifTool/ISO.pm +1 -1
  79. data/bin/lib/Image/ExifTool/ITC.pm +1 -1
  80. data/bin/lib/Image/ExifTool/Import.pm +13 -9
  81. data/bin/lib/Image/ExifTool/InDesign.pm +3 -5
  82. data/bin/lib/Image/ExifTool/JPEG.pm +22 -11
  83. data/bin/lib/Image/ExifTool/JPEGDigest.pm +1 -1
  84. data/bin/lib/Image/ExifTool/JSON.pm +3 -3
  85. data/bin/lib/Image/ExifTool/JVC.pm +1 -1
  86. data/bin/lib/Image/ExifTool/Jpeg2000.pm +2 -2
  87. data/bin/lib/Image/ExifTool/Kodak.pm +1233 -58
  88. data/bin/lib/Image/ExifTool/KyoceraRaw.pm +1 -1
  89. data/bin/lib/Image/ExifTool/LNK.pm +1 -1
  90. data/bin/lib/Image/ExifTool/Lang/cs.pm +1 -1
  91. data/bin/lib/Image/ExifTool/Lang/de.pm +33 -24
  92. data/bin/lib/Image/ExifTool/Lang/en_ca.pm +64 -2
  93. data/bin/lib/Image/ExifTool/Lang/en_gb.pm +64 -2
  94. data/bin/lib/Image/ExifTool/Lang/es.pm +8 -4
  95. data/bin/lib/Image/ExifTool/Lang/fi.pm +46 -4
  96. data/bin/lib/Image/ExifTool/Lang/fr.pm +5 -3
  97. data/bin/lib/Image/ExifTool/Lang/it.pm +6 -3
  98. data/bin/lib/Image/ExifTool/Lang/ja.pm +15 -3
  99. data/bin/lib/Image/ExifTool/Lang/ko.pm +5 -2
  100. data/bin/lib/Image/ExifTool/Lang/nl.pm +6 -3
  101. data/bin/lib/Image/ExifTool/Lang/pl.pm +2 -2
  102. data/bin/lib/Image/ExifTool/Lang/ru.pm +1 -1
  103. data/bin/lib/Image/ExifTool/Lang/sv.pm +1 -1
  104. data/bin/lib/Image/ExifTool/Lang/tr.pm +4 -2
  105. data/bin/lib/Image/ExifTool/Lang/zh_cn.pm +1 -1
  106. data/bin/lib/Image/ExifTool/Lang/zh_tw.pm +1 -1
  107. data/bin/lib/Image/ExifTool/Leaf.pm +1 -1
  108. data/bin/lib/Image/ExifTool/Lytro.pm +4 -8
  109. data/bin/lib/Image/ExifTool/M2TS.pm +10 -9
  110. data/bin/lib/Image/ExifTool/MIE.pm +12 -8
  111. data/bin/lib/Image/ExifTool/MIEUnits.pod +1 -1
  112. data/bin/lib/Image/ExifTool/MIFF.pm +1 -1
  113. data/bin/lib/Image/ExifTool/MNG.pm +1 -1
  114. data/bin/lib/Image/ExifTool/MOI.pm +1 -1
  115. data/bin/lib/Image/ExifTool/MPC.pm +1 -1
  116. data/bin/lib/Image/ExifTool/MPEG.pm +2 -3
  117. data/bin/lib/Image/ExifTool/MPF.pm +6 -6
  118. data/bin/lib/Image/ExifTool/MWG.pm +4 -4
  119. data/bin/lib/Image/ExifTool/MXF.pm +2 -2
  120. data/bin/lib/Image/ExifTool/MacOS.pm +184 -34
  121. data/bin/lib/Image/ExifTool/MakerNotes.pm +101 -18
  122. data/bin/lib/Image/ExifTool/Matroska.pm +1 -1
  123. data/bin/lib/Image/ExifTool/Microsoft.pm +5 -3
  124. data/bin/lib/Image/ExifTool/Minolta.pm +89 -62
  125. data/bin/lib/Image/ExifTool/MinoltaRaw.pm +1 -1
  126. data/bin/lib/Image/ExifTool/Motorola.pm +1 -1
  127. data/bin/lib/Image/ExifTool/Nikon.pm +1511 -380
  128. data/bin/lib/Image/ExifTool/NikonCapture.pm +1 -1
  129. data/bin/lib/Image/ExifTool/NikonCustom.pm +2758 -2935
  130. data/bin/lib/Image/ExifTool/Nintendo.pm +1 -1
  131. data/bin/lib/Image/ExifTool/OOXML.pm +1 -1
  132. data/bin/lib/Image/ExifTool/Ogg.pm +1 -1
  133. data/bin/lib/Image/ExifTool/Olympus.pm +47 -8
  134. data/bin/lib/Image/ExifTool/OpenEXR.pm +1 -1
  135. data/bin/lib/Image/ExifTool/Opus.pm +1 -1
  136. data/bin/lib/Image/ExifTool/PCX.pm +138 -0
  137. data/bin/lib/Image/ExifTool/PDF.pm +58 -42
  138. data/bin/lib/Image/ExifTool/PGF.pm +1 -1
  139. data/bin/lib/Image/ExifTool/PICT.pm +1 -1
  140. data/bin/lib/Image/ExifTool/PLIST.pm +12 -5
  141. data/bin/lib/Image/ExifTool/PLUS.pm +1 -1
  142. data/bin/lib/Image/ExifTool/PNG.pm +108 -10
  143. data/bin/lib/Image/ExifTool/PPM.pm +3 -3
  144. data/bin/lib/Image/ExifTool/PSP.pm +1 -1
  145. data/bin/lib/Image/ExifTool/Palm.pm +1 -1
  146. data/bin/lib/Image/ExifTool/Panasonic.pm +299 -31
  147. data/bin/lib/Image/ExifTool/PanasonicRaw.pm +201 -19
  148. data/bin/lib/Image/ExifTool/Pentax.pm +164 -143
  149. data/bin/lib/Image/ExifTool/PhaseOne.pm +12 -5
  150. data/bin/lib/Image/ExifTool/PhotoCD.pm +9 -10
  151. data/bin/lib/Image/ExifTool/PhotoMechanic.pm +1 -1
  152. data/bin/lib/Image/ExifTool/Photoshop.pm +230 -60
  153. data/bin/lib/Image/ExifTool/PostScript.pm +29 -4
  154. data/bin/lib/Image/ExifTool/PrintIM.pm +1 -1
  155. data/bin/lib/Image/ExifTool/Qualcomm.pm +2 -2
  156. data/bin/lib/Image/ExifTool/QuickTime.pm +1539 -279
  157. data/bin/lib/Image/ExifTool/QuickTimeStream.pl +1857 -0
  158. data/bin/lib/Image/ExifTool/README +84 -46
  159. data/bin/lib/Image/ExifTool/RIFF.pm +116 -23
  160. data/bin/lib/Image/ExifTool/RSRC.pm +1 -1
  161. data/bin/lib/Image/ExifTool/RTF.pm +6 -4
  162. data/bin/lib/Image/ExifTool/Radiance.pm +1 -1
  163. data/bin/lib/Image/ExifTool/Rawzor.pm +3 -2
  164. data/bin/lib/Image/ExifTool/Real.pm +1 -1
  165. data/bin/lib/Image/ExifTool/Reconyx.pm +261 -7
  166. data/bin/lib/Image/ExifTool/Red.pm +325 -0
  167. data/bin/lib/Image/ExifTool/Ricoh.pm +3 -7
  168. data/bin/lib/Image/ExifTool/Samsung.pm +95 -25
  169. data/bin/lib/Image/ExifTool/Sanyo.pm +1 -1
  170. data/bin/lib/Image/ExifTool/Scalado.pm +1 -1
  171. data/bin/lib/Image/ExifTool/Shift.pl +26 -12
  172. data/bin/lib/Image/ExifTool/Shortcuts.pm +9 -2
  173. data/bin/lib/Image/ExifTool/Sigma.pm +36 -30
  174. data/bin/lib/Image/ExifTool/SigmaRaw.pm +3 -8
  175. data/bin/lib/Image/ExifTool/Sony.pm +531 -177
  176. data/bin/lib/Image/ExifTool/SonyIDC.pm +63 -3
  177. data/bin/lib/Image/ExifTool/Stim.pm +2 -2
  178. data/bin/lib/Image/ExifTool/TagInfoXML.pm +23 -23
  179. data/bin/lib/Image/ExifTool/TagLookup.pm +6352 -5062
  180. data/bin/lib/Image/ExifTool/TagNames.pod +3024 -565
  181. data/bin/lib/Image/ExifTool/Theora.pm +1 -1
  182. data/bin/lib/Image/ExifTool/Torrent.pm +2 -2
  183. data/bin/lib/Image/ExifTool/Unknown.pm +1 -1
  184. data/bin/lib/Image/ExifTool/VCard.pm +47 -9
  185. data/bin/lib/Image/ExifTool/Validate.pm +391 -99
  186. data/bin/lib/Image/ExifTool/Vorbis.pm +1 -1
  187. data/bin/lib/Image/ExifTool/WTV.pm +319 -0
  188. data/bin/lib/Image/ExifTool/WriteCanonRaw.pl +1 -1
  189. data/bin/lib/Image/ExifTool/WriteExif.pl +91 -18
  190. data/bin/lib/Image/ExifTool/WriteIPTC.pl +6 -6
  191. data/bin/lib/Image/ExifTool/WritePDF.pl +13 -12
  192. data/bin/lib/Image/ExifTool/WritePNG.pl +1 -1
  193. data/bin/lib/Image/ExifTool/WritePhotoshop.pl +1 -1
  194. data/bin/lib/Image/ExifTool/WritePostScript.pl +2 -2
  195. data/bin/lib/Image/ExifTool/WriteQuickTime.pl +764 -121
  196. data/bin/lib/Image/ExifTool/WriteXMP.pl +176 -67
  197. data/bin/lib/Image/ExifTool/Writer.pl +490 -246
  198. data/bin/lib/Image/ExifTool/XMP.pm +216 -76
  199. data/bin/lib/Image/ExifTool/XMP2.pl +54 -10
  200. data/bin/lib/Image/ExifTool/XMPStruct.pl +14 -11
  201. data/bin/lib/Image/ExifTool/ZIP.pm +60 -15
  202. data/bin/lib/Image/ExifTool/iWork.pm +12 -5
  203. data/bin/perl-Image-ExifTool.spec +46 -44
  204. data/lib/exiftool_vendored/version.rb +1 -1
  205. metadata +14 -4
@@ -15,7 +15,7 @@ use vars qw($VERSION);
15
15
  use Image::ExifTool qw(:DataAccess :Utils);
16
16
  use Image::ExifTool::Exif;
17
17
 
18
- $VERSION = '1.04';
18
+ $VERSION = '1.06';
19
19
 
20
20
  sub WritePhaseOne($$$);
21
21
  sub ProcessPhaseOne($$$);
@@ -85,6 +85,7 @@ my @formatName = ( undef, 'string', 'int16s', undef, 'int32s' );
85
85
  Binary => 1,
86
86
  PutFirst => 1,
87
87
  Writable => 0,
88
+ Drop => 1, # don't copy to other file types
88
89
  },
89
90
  0x0110 => { #1
90
91
  Name => 'SensorCalibration',
@@ -259,6 +260,7 @@ my @formatName = ( undef, 'string', 'int16s', undef, 'int32s' );
259
260
  CHECK_PROC => \&Image::ExifTool::Exif::CheckExif,
260
261
  GROUPS => { 0 => 'MakerNotes', 2 => 'Camera' },
261
262
  TAG_PREFIX => 'SensorCalibration',
263
+ WRITE_GROUP => 'PhaseOne',
262
264
  VARS => { ENTRY_SIZE => 12 }, # (entries do not contain a format field)
263
265
  0x0400 => {
264
266
  Name => 'SensorDefects',
@@ -434,7 +436,7 @@ sub WritePhaseOne($$$)
434
436
 
435
437
  # nothing to do if we aren't changing any PhaseOne tags
436
438
  my $newTags = $et->GetNewTagInfoHash($tagTablePtr);
437
- return undef unless %$newTags;
439
+ return undef unless %$newTags or $$et{DropTags} or $$et{EDIT_DIRS}{PhaseOne};
438
440
 
439
441
  my $dataPt = $$dirInfo{DataPt};
440
442
  my $dataPos = $$dirInfo{DataPos} || 0;
@@ -502,7 +504,8 @@ sub WritePhaseOne($$$)
502
504
  $valuePtr += $dirStart;
503
505
  }
504
506
  my $value = substr($$dataPt, $valuePtr, $size);
505
- my $tagInfo = $$newTags{$tagID} || $et->GetTagInfo($tagTablePtr, $tagID);
507
+ my $tagInfo = $$newTags{$tagID} || $$tagTablePtr{$tagID};
508
+ $tagInfo = $et->GetTagInfo($tagTablePtr, $tagID) if $tagInfo and ref($tagInfo) ne 'HASH';
506
509
  if ($$newTags{$tagID}) {
507
510
  $formatStr = $$tagInfo{Format} if $$tagInfo{Format};
508
511
  my $count = int($size / Image::ExifTool::FormatSize($formatStr));
@@ -533,6 +536,10 @@ sub WritePhaseOne($$$)
533
536
  $value = $newValue;
534
537
  $size = length $newValue;
535
538
  }
539
+ } elsif ($$et{DropTags} and (($tagInfo and $$tagInfo{Drop}) or $size > 8192)) {
540
+ # decrease the number of entries in the directory
541
+ Set32u(Get32u(\$dirBuff, 0) - 1, \$dirBuff, 0);
542
+ next; # drop this tag
536
543
  }
537
544
  # add the tagID, possibly format size, and size to this directory entry
538
545
  $dirBuff .= substr($$dataPt, $entry, $entrySize - 8) . Set32u($size);
@@ -571,7 +578,7 @@ sub ProcessPhaseOne($$$)
571
578
  {
572
579
  my ($et, $dirInfo, $tagTablePtr) = @_;
573
580
  my $dataPt = $$dirInfo{DataPt};
574
- my $dataPos = $$dirInfo{DataPos} || 0;
581
+ my $dataPos = ($$dirInfo{DataPos} || 0) + ($$dirInfo{Base} || 0);
575
582
  my $dirStart = $$dirInfo{DirStart} || 0;
576
583
  my $dirLen = $$dirInfo{DirLen} || $$dirInfo{DataLen} - $dirStart;
577
584
  my $binary = $et->Options('Binary');
@@ -704,7 +711,7 @@ One maker notes.
704
711
 
705
712
  =head1 AUTHOR
706
713
 
707
- Copyright 2003-2017, Phil Harvey (phil at owl.phy.queensu.ca)
714
+ Copyright 2003-2019, Phil Harvey (phil at owl.phy.queensu.ca)
708
715
 
709
716
  This library is free software; you can redistribute it and/or modify it
710
717
  under the same terms as Perl itself.
@@ -13,9 +13,8 @@ package Image::ExifTool::PhotoCD;
13
13
  use strict;
14
14
  use vars qw($VERSION);
15
15
  use Image::ExifTool qw(:DataAccess :Utils);
16
- use Image::ExifTool::Exif; # (for Composite:ImageSize)
17
16
 
18
- $VERSION = '1.01';
17
+ $VERSION = '1.03';
19
18
 
20
19
  sub ProcessExtData($$$);
21
20
 
@@ -411,22 +410,22 @@ sub ProcessExtData($$$);
411
410
  1538.1 => {
412
411
  Name => 'ImageWidth',
413
412
  Mask => 0x0c,
414
- # 0x00=Base (768x512), 0x04=4Base (1536x1024), 0x08=16Base (3072x2048)
415
- ValueConv => '($$self{Orient} & 0x01 ? 512 : 768) * (($val || 2) / 2)',
413
+ # 0=Base (768x512), 1=4Base (1536x1024), 2=16Base (3072x2048)
414
+ ValueConv => '($$self{Orient} & 0x01 ? 512 : 768) * ($val * 2 || 1)',
416
415
  },
417
416
  1538.2 => {
418
417
  Name => 'ImageHeight',
419
418
  Mask => 0x0c,
420
- ValueConv => '($$self{Orient} & 0x01 ? 768 : 512) * (($val || 2) / 2)',
419
+ ValueConv => '($$self{Orient} & 0x01 ? 768 : 512) * ($val * 2 || 1)',
421
420
  },
422
421
  1538.3 => {
423
422
  Name => 'CompressionClass',
424
423
  Mask => 0x60,
425
424
  PrintConv => {
426
- 0x00 => 'Class 1 - 35mm film; Pictoral hard copy',
427
- 0x20 => 'Class 2 - Large format film',
428
- 0x40 => 'Class 3 - Text and graphics, high resolution',
429
- 0x60 => 'Class 4 - Text and graphics, high dynamic range',
425
+ 0 => 'Class 1 - 35mm film; Pictoral hard copy',
426
+ 1 => 'Class 2 - Large format film',
427
+ 2 => 'Class 3 - Text and graphics, high resolution',
428
+ 3 => 'Class 4 - Text and graphics, high dynamic range',
430
429
  },
431
430
  },
432
431
  #1544 => 'InterleaveRatio',
@@ -485,7 +484,7 @@ information from Kodak Photo CD Image Pac (PCD) files.
485
484
 
486
485
  =head1 AUTHOR
487
486
 
488
- Copyright 2003-2017, Phil Harvey (phil at owl.phy.queensu.ca)
487
+ Copyright 2003-2019, Phil Harvey (phil at owl.phy.queensu.ca)
489
488
 
490
489
  This library is free software; you can redistribute it and/or modify it
491
490
  under the same terms as Perl itself.
@@ -236,7 +236,7 @@ write information written by the Camera Bits Photo Mechanic software.
236
236
 
237
237
  =head1 AUTHOR
238
238
 
239
- Copyright 2003-2017, Phil Harvey (phil at owl.phy.queensu.ca)
239
+ Copyright 2003-2019, Phil Harvey (phil at owl.phy.queensu.ca)
240
240
 
241
241
  This library is free software; you can redistribute it and/or modify it
242
242
  under the same terms as Perl itself.
@@ -28,7 +28,7 @@ use strict;
28
28
  use vars qw($VERSION $AUTOLOAD $iptcDigestInfo);
29
29
  use Image::ExifTool qw(:DataAccess :Utils);
30
30
 
31
- $VERSION = '1.56';
31
+ $VERSION = '1.63';
32
32
 
33
33
  sub ProcessPhotoshop($$$);
34
34
  sub WritePhotoshop($$$);
@@ -486,7 +486,13 @@ my %unicodeString = (
486
486
  # tags extracted from layer information
487
487
  # (tag ID's are for convenience only)
488
488
  _xcnt => { Name => 'LayerCount', Format => 'int16u' },
489
- _xrct => { Name => 'LayerRectangles', List => 1, Format => 'int32u', Count => 4 },
489
+ _xrct => {
490
+ Name => 'LayerRectangles',
491
+ Format => 'int32u',
492
+ Count => 4,
493
+ List => 1,
494
+ Notes => 'top left bottom right',
495
+ },
490
496
  _xnam => { Name => 'LayerNames',
491
497
  Format => 'string',
492
498
  List => 1,
@@ -499,6 +505,7 @@ my %unicodeString = (
499
505
  Name => 'LayerBlendModes',
500
506
  Format => 'undef',
501
507
  List => 1,
508
+ RawConv => 'GetByteOrder() eq "II" ? pack "N*", unpack "V*", $val : $val',
502
509
  PrintConv => {
503
510
  pass => 'Pass Through',
504
511
  norm => 'Normal',
@@ -562,13 +569,27 @@ my %unicodeString = (
562
569
  Groups => { 2 => 'Time' },
563
570
  List => 1,
564
571
  RawConv => q{
565
- return '' unless $val =~ /layerTimedoub(.{8})/s;
566
- my $tmp = $1;
572
+ return '' unless $val =~ /layerTime(doub|buod)(.{8})/s;
573
+ my $tmp = $2;
567
574
  return GetDouble(\$tmp, 0);
568
575
  },
569
576
  ValueConv => 'length $val ? ConvertUnixTime($val,1) : ""',
570
577
  PrintConv => 'length $val ? $self->ConvertDateTime($val) : ""',
571
- }
578
+ },
579
+ );
580
+
581
+ # tags extracted from ImageSourceData found in TIFF images (ref PH)
582
+ %Image::ExifTool::Photoshop::DocumentData = (
583
+ PROCESS_PROC => \&ProcessDocumentData,
584
+ GROUPS => { 2 => 'Image' },
585
+ Layr => {
586
+ Name => 'Layers',
587
+ SubDirectory => { TagTable => 'Image::ExifTool::Photoshop::Layers' },
588
+ },
589
+ Lr16 => { # (NC)
590
+ Name => 'Layers',
591
+ SubDirectory => { TagTable => 'Image::ExifTool::Photoshop::Layers' },
592
+ },
572
593
  );
573
594
 
574
595
  # image data
@@ -626,16 +647,16 @@ sub ConvertPascalString($$)
626
647
  }
627
648
 
628
649
  #------------------------------------------------------------------------------
629
- # Process Photoshop layers and mask information
650
+ # Process Photoshop layers and mask information section of PSD/PSB file
630
651
  # Inputs: 0) ExifTool ref, 1) DirInfo ref, 2) tag table ref
631
652
  # Returns: 1 on success (and seeks to the end of this section)
632
- sub ProcessLayers($$$)
653
+ sub ProcessLayersAndMask($$$)
633
654
  {
634
655
  local $_;
635
656
  my ($et, $dirInfo, $tagTablePtr) = @_;
636
657
  my $raf = $$dirInfo{RAF};
637
658
  my $fileType = $$et{VALUE}{FileType};
638
- my ($i, $data, $dat2, %count);
659
+ my $data;
639
660
 
640
661
  return 0 unless $fileType eq 'PSD' or $fileType eq 'PSB'; # (no layer section in CS1 files)
641
662
 
@@ -644,91 +665,222 @@ sub ProcessLayers($$$)
644
665
 
645
666
  # read the layer information header
646
667
  my $n = $psiz * 2 + 2;
647
- my $dataPos = $raf->Tell();
648
668
  $raf->Read($data, $n) == $n or return 0;
649
- my %dinfo = ( DataPt => \$data, DataPos => $dataPos );
650
669
  my $tot = $psb ? Get64u(\$data, 0) : Get32u(\$data, 0); # length of layer and mask info
651
- my $len = $psb ? Get64u(\$data, $psiz) : Get32u(\$data, $psiz); # length of layer info section
652
- my $num = Get16s(\$data, $psiz * 2);
670
+ return 1 if $tot == 0;
671
+ my $end = $raf->Tell() - $psiz - 2 + $tot;
672
+ $data = substr $data, $psiz;
673
+ my $len = $psb ? Get64u(\$data, 0) : Get32u(\$data, 0); # length of layer info section
674
+ my $num = Get16s(\$data, $psiz);
675
+ # check for Lr16 block if layers length is 0 (ref https://forums.adobe.com/thread/1540914)
676
+ if ($len == 0 and $num == 0) {
677
+ $raf->Read($data,10) == 10 or return 0;
678
+ if ($data =~/^..8BIMLr16/s) {
679
+ $raf->Read($data, $psiz+2) == $psiz+2 or return 0;
680
+ $len = $psb ? Get64u(\$data, 0) : Get32u(\$data, 0);
681
+ } else {
682
+ $raf->Seek(-10, 1) or return 0;
683
+ }
684
+ }
685
+ $len += 2; # include layer count with layer info section
686
+ $raf->Seek(-2, 1) or return 0;
687
+ my %dinfo = (
688
+ RAF => $raf,
689
+ DirLen => $len,
690
+ );
691
+ $$et{IsPSB} = $psb; # set PSB flag
692
+ ProcessLayers($et, \%dinfo, $tagTablePtr);
693
+
694
+ # seek to the end of this section and return success flag
695
+ return $raf->Seek($end, 0) ? 1 : 0;
696
+ }
697
+
698
+ #------------------------------------------------------------------------------
699
+ # Process Photoshop layers (beginning with layer count)
700
+ # Inputs: 0) ExifTool ref, 1) DirInfo ref, 2) tag table ref
701
+ # Returns: 1 on success
702
+ # Notes: Uses ExifTool IsPSB member to determine whether file is PSB format
703
+ sub ProcessLayers($$$)
704
+ {
705
+ local $_;
706
+ my ($et, $dirInfo, $tagTablePtr) = @_;
707
+ my ($i, $n, %count, $buff, $buf2);
708
+ my $raf = $$dirInfo{RAF};
709
+ my $dirLen = $$dirInfo{DirLen};
710
+ my $verbose = $$et{OPTIONS}{Verbose};
711
+ my %dinfo = ( DataPt => \$buff, Base => $raf->Tell() );
712
+ my $pos = 0;
713
+ return 0 if $dirLen < 2;
714
+ $raf->Read($buff, 2) == 2 or return 0;
715
+ my $num = Get16s(\$buff, 0);
653
716
  $num = -$num if $num < 0; # (first channel is transparency data if negative)
654
- $et->HandleTag($tagTablePtr, '_xcnt', $num, Start => $psiz*2, Size => 2, %dinfo); # LayerCount
655
- $et->VerboseDir('Layers', $num, $len);
656
- $dataPos += $n; # point to start of layer information section
717
+ $et->VerboseDir('Layers', $num, $dirLen);
718
+ $et->HandleTag($tagTablePtr, '_xcnt', $num, Start => $pos, Size => 2, %dinfo); # LayerCount
657
719
  my $oldIndent = $$et{INDENT};
658
720
  $$et{INDENT} .= '| ';
659
721
 
660
- my $pos = 0;
722
+ $pos += 2;
723
+ my $psb = $$et{IsPSB}; # is PSB format?
724
+ my $psiz = $psb ? 8 : 4;
661
725
  for ($i=0; $i<$num; ++$i) {
662
726
  $et->VPrint(0, $oldIndent.'+ [Layer '.($i+1)." of $num]\n");
663
- last if $pos + 18 > $len;
664
- # read the layer information data
665
- $raf->Seek($dataPos + $pos, 0) and $raf->Read($data, 18) == 18 or last;
666
- $dinfo{DataPos} = $dataPos + $pos;
727
+ last if $pos + 18 > $dirLen;
728
+ $raf->Read($buff, 18) == 18 or last;
729
+ $dinfo{DataPos} = $pos;
667
730
  # save the layer rectangle
668
- $et->HandleTag($tagTablePtr, '_xrct', undef, Size => 16, %dinfo);
669
- my $numChannels = Get16u(\$data, 16);
670
- $pos += 18 + (2 + $psiz) * $numChannels; # skip the channel information
671
- last if $pos + 20 > $len;
672
- $raf->Seek($dinfo{DataPos} = $dataPos + $pos, 0) or last;
673
- $raf->Read($data, 20) == 20 and substr($data, 0, 4) eq '8BIM' or last; # verify signature
731
+ $et->HandleTag($tagTablePtr, '_xrct', undef, Start => 0, Size => 16, %dinfo);
732
+ my $numChannels = Get16u(\$buff, 16);
733
+ $n = (2 + $psiz) * $numChannels; # size of channel information
734
+ $raf->Seek($n, 1) or last;
735
+ $pos += 18 + $n;
736
+ last if $pos + 20 > $dirLen;
737
+ $raf->Read($buff, 20) == 20 or last;
738
+ $dinfo{DataPos} = $pos;
739
+ my $sig = substr($buff, 0, 4);
740
+ $sig =~ /^(8BIM|MIB8)$/ or last; # verify signature
674
741
  $et->HandleTag($tagTablePtr, '_xbnd', undef, Start => 4, Size => 4, %dinfo);
675
742
  $et->HandleTag($tagTablePtr, '_xopc', undef, Start => 8, Size => 1, %dinfo);
676
- my $nxt = $pos + 16 + Get32u(\$data, 12);
677
- $n = Get32u(\$data, 16); # get size of layer mask data
743
+ my $nxt = $pos + 16 + Get32u(\$buff, 12);
744
+ $n = Get32u(\$buff, 16); # get size of layer mask data
678
745
  $pos += 20 + $n; # skip layer mask data
679
- last if $pos + 4 > $len;
680
- $raf->Seek($dataPos + $pos, 0) or last;
681
- $raf->Read($data, 4) == 4 or last;
682
- $n = Get32u(\$data, 0); # get size of layer blending ranges
746
+ last if $pos + 4 > $dirLen;
747
+ $raf->Seek($n, 1) and $raf->Read($buff, 4) == 4 or last;
748
+ $n = Get32u(\$buff, 0); # get size of layer blending ranges
683
749
  $pos += 4 + $n; # skip layer blending ranges data
684
- last if $pos + 1 > $len;
685
- $raf->Seek($dataPos + $pos, 0) or last;
686
- $raf->Read($data, 1) == 1 or last;
687
- $n = Get8u(\$data, 0); # get length of layer name
688
- last if $pos + 1 + $n > $len;
689
- $raf->Read($data, $n) == $n or last;
690
- $dinfo{DataPos} = $dataPos + $pos + 1;
691
- $et->HandleTag($tagTablePtr, '_xnam', undef, Size => $n, %dinfo);
750
+ last if $pos + 1 > $dirLen;
751
+ $raf->Seek($n, 1) and $raf->Read($buff, 1) == 1 or last;
752
+ $n = Get8u(\$buff, 0); # get length of layer name
753
+ last if $pos + 1 + $n > $dirLen;
754
+ $raf->Read($buff, $n) == $n or last;
755
+ $dinfo{DataPos} = $pos + 1;
756
+ $et->HandleTag($tagTablePtr, '_xnam', undef, Start => 0, Size => $n, %dinfo);
757
+ my $frag = ($n + 1) & 0x3;
758
+ $raf->Seek(4 - $frag, 1) or last if $frag;
692
759
  $n = ($n + 4) & 0xfffffffc; # +1 for length byte then pad to multiple of 4 bytes
693
760
  $pos += $n;
694
761
  # process additional layer info
695
762
  while ($pos + 12 <= $nxt) {
696
- $raf->Seek($dataPos + $pos, 0) and $raf->Read($data, 12) == 12 or last;
697
- my $sig = substr($data, 0, 4);
763
+ $raf->Read($buff, 12) == 12 or last;
764
+ my $dat = substr($buff, 0, 8);
765
+ $dat = pack 'N*', unpack 'V*', $dat if GetByteOrder() eq 'II';
766
+ my $sig = substr($dat, 0, 4);
698
767
  last unless $sig eq '8BIM' or $sig eq '8B64'; # verify signature
699
- my $tag = substr($data, 4, 4);
768
+ my $tag = substr($dat, 4, 4);
700
769
  # (some structures have an 8-byte size word [augh!]
701
770
  # --> it would be great if '8B64' indicated a 64-bit version, and this may well
702
771
  # be the case, but it is not mentioned in the Photoshop file format specification)
703
772
  if ($psb and $tag =~ /^(LMsk|Lr16|Lr32|Layr|Mt16|Mt32|Mtrn|Alph|FMsk|lnk2|FEid|FXid|PxSD)$/) {
704
773
  last if $pos + 16 > $nxt;
705
- $raf->Read($dat2, 4) == 4 or last;
706
- $data .= $dat2;
707
- $n = Get64u(\$data, 8);
774
+ $raf->Read($buf2, 4) == 4 or last;
775
+ $buff .= $buf2;
776
+ $n = Get64u(\$buff, 8);
708
777
  $pos += 4;
709
778
  } else {
710
- $n = Get32u(\$data, 8);
779
+ $n = Get32u(\$buff, 8);
711
780
  }
712
781
  $pos += 12;
713
782
  last if $pos + $n > $nxt;
714
- $raf->Read($data, $n) == $n or last;
715
- $dinfo{DataPos} = $dataPos + $pos;
716
- # pad with empty entries if necessary to keep the same index for each item in the layer
717
- $count{$tag} = 0 unless defined $count{$tag};
718
- while ($count{$tag} < $i) {
719
- $et->HandleTag($tagTablePtr, $tag, '');
783
+ $frag = $n & 0x3;
784
+ if ($$tagTablePtr{$tag} or $verbose) {
785
+ # pad with empty entries if necessary to keep the same index for each item in the layer
786
+ $count{$tag} = 0 unless defined $count{$tag};
787
+ $raf->Read($buff, $n) == $n or last;
788
+ $dinfo{DataPos} = $pos;
789
+ while ($count{$tag} < $i) {
790
+ $et->HandleTag($tagTablePtr, $tag, '');
791
+ ++$count{$tag};
792
+ }
793
+ $et->HandleTag($tagTablePtr, $tag, undef, Start => 0, Size => $n, %dinfo);
720
794
  ++$count{$tag};
795
+ if ($frag) {
796
+ $raf->Seek(4 - $frag, 1) or last;
797
+ $n += 4 - $frag; # pad to multiple of 4 bytes (PH NC)
798
+ }
799
+ } else {
800
+ $n += 4 - $frag if $frag;
801
+ $raf->Seek($n, 1) or last;
721
802
  }
722
- $et->HandleTag($tagTablePtr, $tag, undef, %dinfo);
723
- ++$count{$tag};
724
803
  $pos += $n; # step to start of next structure
725
804
  }
726
805
  $pos = $nxt;
727
806
  }
728
807
  $$et{INDENT} = $oldIndent;
729
- # seek to the end of this section
730
- return 0 unless $raf->Seek($dataPos - 2 - $psiz + $tot, 0);
731
- return 1; # success!
808
+ return 1;
809
+ }
810
+
811
+ #------------------------------------------------------------------------------
812
+ # Process Photoshop ImageSourceData
813
+ # Inputs: 0) ExifTool ref, 1) dirInfo ref, 2) tag table ref
814
+ # Returns: 1 on success
815
+ sub ProcessDocumentData($$$)
816
+ {
817
+ my ($et, $dirInfo, $tagTablePtr) = @_;
818
+ my $verbose = $$et{OPTIONS}{Verbose};
819
+ my $raf = $$dirInfo{RAF};
820
+ my $dirLen = $$dirInfo{DirLen};
821
+ my $pos = 36; # length of header
822
+ my $buff;
823
+
824
+ $et->VerboseDir('Photoshop Document Data', undef, $dirLen);
825
+ unless ($raf) {
826
+ my $dataPt = $$dirInfo{DataPt};
827
+ my $start = $$dirInfo{DirStart} || 0;
828
+ $raf = new File::RandomAccess($dataPt);
829
+ $raf->Seek($start, 0) if $start;
830
+ $dirLen = length $$dataPt - $start unless defined $dirLen;
831
+ $et->VerboseDump($dataPt, Start => $start, Len => $dirLen, Base => $$dirInfo{Base});
832
+ }
833
+ unless ($raf->Read($buff, $pos) == $pos and
834
+ $buff =~ /^Adobe Photoshop Document Data (Block|V0002)\0/)
835
+ {
836
+ $et->Warn('Invalid Photoshop Document Data');
837
+ return 0;
838
+ }
839
+ my $psb = ($1 eq 'V0002');
840
+ my %dinfo = ( DataPt => \$buff );
841
+ my ($n, $setOrder);
842
+ $$et{IsPSB} = $psb; # set PSB flag (needed when handling Layers directory)
843
+ while ($pos + 12 <= $dirLen) {
844
+ $raf->Read($buff, 8) == 8 or last;
845
+ # set byte order according to byte order of first signature
846
+ SetByteOrder($buff =~ /^(8BIM|8B64)/ ? 'MM' : 'II') if $pos == 36;
847
+ $buff = pack 'N*', unpack 'V*', $buff if GetByteOrder() eq 'II';
848
+ my $sig = substr($buff, 0, 4);
849
+ last unless $sig eq '8BIM' or $sig eq '8B64'; # verify signature
850
+ my $tag = substr($buff, 4, 4);
851
+ if ($psb and $tag =~ /^(LMsk|Lr16|Lr32|Layr|Mt16|Mt32|Mtrn|Alph|FMsk|lnk2|FEid|FXid|PxSD)$/) {
852
+ last if $pos + 16 > $dirLen;
853
+ $raf->Read($buff, 8) == 8 or last;
854
+ $n = Get64u(\$buff, 0);
855
+ $pos += 4;
856
+ } else {
857
+ $raf->Read($buff, 4) == 4 or last;
858
+ $n = Get32u(\$buff, 0);
859
+ }
860
+ $pos += 12;
861
+ last if $pos + $n > $dirLen;
862
+ my $pad = (4 - ($n & 3)) & 3; # number of padding bytes
863
+ my $tagInfo = $$tagTablePtr{$tag};
864
+ if ($tagInfo or $verbose) {
865
+ if ($tagInfo and $$tagInfo{SubDirectory}) {
866
+ my $fpos = $raf->Tell() + $n + $pad;
867
+ my $subTable = GetTagTable($$tagInfo{SubDirectory}{TagTable});
868
+ $et->ProcessDirectory({ RAF => $raf, DirLen => $n }, $subTable);
869
+ $raf->Seek($fpos, 0) or last;
870
+ } else {
871
+ $dinfo{DataPos} = $raf->Tell();
872
+ $dinfo{Start} = 0;
873
+ $dinfo{Size} = $n;
874
+ $raf->Read($buff, $n) == $n or last;
875
+ $et->HandleTag($tagTablePtr, $tag, undef, %dinfo);
876
+ $raf->Seek($pad, 1) or last;
877
+ }
878
+ } else {
879
+ $raf->Seek($n + $pad, 1) or last;
880
+ }
881
+ $pos += $n + $pad; # step to start of next structure
882
+ }
883
+ return 1;
732
884
  }
733
885
 
734
886
  #------------------------------------------------------------------------------
@@ -745,6 +897,23 @@ sub ProcessPhotoshop($$$)
745
897
  my $verbose = $et->Options('Verbose');
746
898
  my $success = 0;
747
899
 
900
+ # ignore non-standard XMP while in strict MWG compatibility mode
901
+ if (($Image::ExifTool::MWG::strict or $et->Options('Validate')) and
902
+ $$et{FILE_TYPE} =~ /^(JPEG|TIFF|PSD)$/)
903
+ {
904
+ my $path = $et->MetadataPath();
905
+ unless ($path =~ /^(JPEG-APP13-Photoshop|TIFF-IFD0-Photoshop|PSD)$/) {
906
+ if ($Image::ExifTool::MWG::strict) {
907
+ $et->Warn("Ignored non-standard Photoshop at $path");
908
+ return 1;
909
+ } else {
910
+ $et->Warn("Non-standard Photoshop at $path", 1);
911
+ }
912
+ }
913
+ }
914
+ if ($$et{FILE_TYPE} eq 'JPEG' and $$dirInfo{Parent} ne 'APP13') {
915
+ $$et{LOW_PRIORITY_DIR}{'*'} = 1; # lower priority of all these tags
916
+ }
748
917
  SetByteOrder('MM'); # Photoshop is always big-endian
749
918
  $verbose and $et->VerboseDir('Photoshop', 0, $$dirInfo{DirLen});
750
919
 
@@ -809,6 +978,7 @@ sub ProcessPhotoshop($$$)
809
978
  $size += 1 if $size & 0x01; # size is padded to an even # bytes
810
979
  $pos += $size;
811
980
  }
981
+ delete $$et{LOW_PRIORITY_DIR}{'*'};
812
982
  return $success;
813
983
  }
814
984
 
@@ -905,7 +1075,7 @@ sub ProcessPSD($$)
905
1075
  $tagTablePtr = GetTagTable('Image::ExifTool::Photoshop::Layers');
906
1076
  my $oldIndent = $$et{INDENT};
907
1077
  $$et{INDENT} .= '| ';
908
- if (ProcessLayers($et, \%dirInfo, $tagTablePtr) and
1078
+ if (ProcessLayersAndMask($et, \%dirInfo, $tagTablePtr) and
909
1079
  # read compression mode from image data section
910
1080
  $raf->Read($data,2) == 2)
911
1081
  {
@@ -957,7 +1127,7 @@ be preserved when copying Photoshop information via user-defined tags.
957
1127
 
958
1128
  =head1 AUTHOR
959
1129
 
960
- Copyright 2003-2017, Phil Harvey (phil at owl.phy.queensu.ca)
1130
+ Copyright 2003-2019, Phil Harvey (phil at owl.phy.queensu.ca)
961
1131
 
962
1132
  This library is free software; you can redistribute it and/or modify it
963
1133
  under the same terms as Perl itself.