123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263 |
- #------------------------------------------------------------------------------
- # File: HP.pm
- #
- # Description: Hewlett-Packard maker notes tags
- #
- # Revisions: 2007-05-03 - P. Harvey Created
- #------------------------------------------------------------------------------
- package Image::ExifTool::HP;
- use strict;
- use vars qw($VERSION);
- use Image::ExifTool qw(:DataAccess :Utils);
- $VERSION = '1.04';
- sub ProcessHP($$$);
- sub ProcessTDHD($$$);
- # HP EXIF-format maker notes (or is it Vivitar?)
- %Image::ExifTool::HP::Main = (
- GROUPS => { 0 => 'MakerNotes', 2 => 'Camera' },
- NOTES => q{
- These tables list tags found in the maker notes of some Hewlett-Packard
- camera models.
- The first table lists tags found in the EXIF-format maker notes of the
- PhotoSmart 720 (also used by the Vivitar ViviCam 3705, 3705B and 3715).
- },
- 0x0e00 => {
- Name => 'PrintIM',
- Description => 'Print Image Matching',
- SubDirectory => {
- TagTable => 'Image::ExifTool::PrintIM::Main',
- },
- },
- );
- # other types of HP maker notes
- %Image::ExifTool::HP::Type2 = (
- PROCESS_PROC => \&ProcessHP,
- GROUPS => { 0 => 'MakerNotes', 2 => 'Camera' },
- NOTES => 'These tags are used by the PhotoSmart E427.',
- 'PreviewImage' => {
- Name => 'PreviewImage',
- Groups => { 2 => 'Preview' },
- RawConv => '$self->ValidateImage(\$val,$tag)',
- },
- 'Serial Number' => 'SerialNumber',
- 'Lens Shading' => 'LensShading',
- );
- %Image::ExifTool::HP::Type4 = (
- PROCESS_PROC => \&Image::ExifTool::ProcessBinaryData,
- GROUPS => { 0 => 'MakerNotes', 2 => 'Camera' },
- NOTES => 'These tags are used by the PhotoSmart M627.',
- 0x0c => {
- Name => 'MaxAperture',
- Format => 'int16u',
- ValueConv => '$val / 10',
- },
- 0x10 => {
- Name => 'ExposureTime',
- Format => 'int32u',
- ValueConv => '$val / 1e6',
- PrintConv => 'Image::ExifTool::Exif::PrintExposureTime($val)',
- },
- 0x14 => {
- Name => 'CameraDateTime',
- Groups => { 2 => 'Time' },
- Format => 'string[20]',
- },
- 0x34 => {
- Name => 'ISO',
- Format => 'int16u',
- },
- 0x5c => {
- Name => 'SerialNumber',
- Format => 'string[26]',
- RawConv => '$val =~ s/^SERIAL NUMBER:// ? $val : undef',
- },
- );
- %Image::ExifTool::HP::Type6 = (
- PROCESS_PROC => \&Image::ExifTool::ProcessBinaryData,
- GROUPS => { 0 => 'MakerNotes', 2 => 'Camera' },
- NOTES => 'These tags are used by the PhotoSmart M425, M525 and M527.',
- 0x0c => {
- Name => 'FNumber',
- Format => 'int16u',
- ValueConv => '$val / 10',
- },
- 0x10 => {
- Name => 'ExposureTime',
- Format => 'int32u',
- ValueConv => '$val / 1e6',
- PrintConv => 'Image::ExifTool::Exif::PrintExposureTime($val)',
- },
- 0x14 => {
- Name => 'CameraDateTime',
- Groups => { 2 => 'Time' },
- Format => 'string[20]',
- },
- 0x34 => {
- Name => 'ISO',
- Format => 'int16u',
- },
- 0x58 => {
- Name => 'SerialNumber',
- Format => 'string[26]',
- RawConv => '$val =~ s/^SERIAL NUMBER:// ? $val : undef',
- },
- );
- # proprietary format TDHD data written by Photosmart R837 (ref PH)
- %Image::ExifTool::HP::TDHD = (
- PROCESS_PROC => \&ProcessTDHD,
- GROUPS => { 0 => 'MakerNotes', 2 => 'Camera' },
- NOTES => q{
- These tags are extracted from the APP6 "TDHD" segment of Photosmart R837
- JPEG images. Many other unknown tags exist in is data, and can be seen with
- the Unknown (-u) option.
- },
- # (all subdirectories except TDHD and LSLV are automatically recognized
- # by their "type" word of 0x10001)
- TDHD => {
- Name => 'TDHD',
- SubDirectory => { TagTable => 'Image::ExifTool::HP::TDHD' },
- },
- LSLV => {
- Name => 'LSLV',
- SubDirectory => { TagTable => 'Image::ExifTool::HP::TDHD' },
- },
- FWRV => 'FirmwareVersion',
- CMSN => 'SerialNumber', # (unverified)
- # LTEM - some temperature?
- );
- #------------------------------------------------------------------------------
- # Process HP APP6 TDHD metadata (ref PH)
- # Inputs: 0) ExifTool object ref, 1) dirInfo ref, 2) tag table ref
- # Returns: 1 on success
- sub ProcessTDHD($$$)
- {
- my ($et, $dirInfo, $tagTablePtr) = @_;
- my $dataPt = $$dirInfo{DataPt};
- my $dataPos = $$dirInfo{DataPos};
- my $pos = $$dirInfo{DirStart};
- my $dirEnd = $pos + $$dirInfo{DirLen};
- my $unknown = $et->Options('Unknown') || $et->Options('Verbose');
- $et->VerboseDir('TDHD', undef, $$dirInfo{DirLen});
- SetByteOrder('II');
- while ($pos + 12 < $dirEnd) {
- my $tag = substr($$dataPt, $pos, 4);
- my $type = Get32u($dataPt, $pos + 4);
- my $size = Get32u($dataPt, $pos + 8);
- $pos += 12;
- last if $size < 0 or $pos + $size > $dirEnd;
- if ($type == 0x10001) {
- # this is a subdirectory containing more tags
- my %dirInfo = (
- DataPt => $dataPt,
- DataPos => $dataPos,
- DirStart => $pos,
- DirLen => $size,
- );
- $et->ProcessDirectory(\%dirInfo, $tagTablePtr);
- } else {
- if (not $$tagTablePtr{$tag} and $unknown) {
- my $name = $tag;
- $name =~ tr/-_A-Za-z0-9//dc; # remove invalid characters
- my %tagInfo = (
- Name => "HP_TDHD_$name",
- Unknown => 1,
- );
- # guess format based on data size
- if ($size == 1) {
- $tagInfo{Format} = 'int8u';
- } elsif ($size == 2) {
- $tagInfo{Format} = 'int16u';
- } elsif ($size == 4) {
- $tagInfo{Format} = 'int32s';
- } elsif ($size > 80) {
- $tagInfo{Binary} = 1;
- }
- AddTagToTable($tagTablePtr, $tag, \%tagInfo);
- }
- $et->HandleTag($tagTablePtr, $tag, undef,
- DataPt => $dataPt,
- DataPos => $dataPos,
- Start => $pos,
- Size => $size,
- );
- }
- $pos += $size;
- }
- return 1;
- }
- #------------------------------------------------------------------------------
- # Process HP maker notes
- # Inputs: 0) ExifTool object ref, 1) dirInfo ref, 2) tag table ref
- # Returns: 1 on success, otherwise returns 0 and sets a Warning
- sub ProcessHP($$$)
- {
- my ($et, $dirInfo, $tagTablePtr) = @_;
- my $dataPt = $$dirInfo{DataPt};
- my $dataLen = $$dirInfo{DataLen};
- my $dirStart = $$dirInfo{DirStart} || 0;
- my $dirLen = $$dirInfo{DirLen} || $dataLen - $dirStart;
- # look for known text-type tags
- if ($dirStart or $dirLen != length($$dataPt)) {
- my $buff = substr($$dataPt, $dirStart, $dirLen);
- $dataPt = \$buff;
- }
- my $tagID;
- # brute-force scan for PreviewImage
- if ($$tagTablePtr{PreviewImage} and $$dataPt =~ /(\xff\xd8\xff\xdb.*\xff\xd9)/gs) {
- $et->HandleTag($tagTablePtr, 'PreviewImage', $1);
- # truncate preview to speed subsequent tag scans
- my $buff = substr($$dataPt, 0, pos($$dataPt)-length($1));
- $dataPt = \$buff;
- }
- # scan for other tag ID's
- foreach $tagID (sort(TagTableKeys($tagTablePtr))) {
- next if $tagID eq 'PreviewImage';
- next unless $$dataPt =~ /$tagID:\s*([\x20-\x7f]+)/i;
- $et->HandleTag($tagTablePtr, $tagID, $1);
- }
- return 1;
- }
- 1; # end
- __END__
- =head1 NAME
- Image::ExifTool::HP - Hewlett-Packard maker notes tags
- =head1 SYNOPSIS
- This module is loaded automatically by Image::ExifTool when required.
- =head1 DESCRIPTION
- This module contains definitions required by Image::ExifTool to interpret
- Hewlett-Packard maker notes.
- =head1 AUTHOR
- Copyright 2003-2016, Phil Harvey (phil at owl.phy.queensu.ca)
- This library is free software; you can redistribute it and/or modify it
- under the same terms as Perl itself.
- =head1 SEE ALSO
- L<Image::ExifTool::TagNames/HP Tags>,
- L<Image::ExifTool(3pm)|Image::ExifTool>
- =cut
|