1 /* =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- */
2 /*          EXIFPROBE - TIFF/JPEG/EXIF image file probe               */
3 /* =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- */
4 /* Copyright (C) 2002,2005 by Duane H. Hesser. All rights reserved.   */
5 /*                                                                    */
6 /* See the file LICENSE.EXIFPROBE for terms of use.                   */
7 /* =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- */
8 
9 #ifndef lint
10 static char *ModuleId = "@(#) $Id: maker_fujifilm.c,v 1.13 2005/07/24 22:56:26 alex Exp $";
11 #endif
12 
13 /* =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- */
14 /* Fujitsu camera maker-specific routines (Fujifilm)                  */
15 /* =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- */
16 /* Most of the information coded here is due to TsuruZoh Tachibanaya  */
17 /* at:                                                                */
18 /* http://www.ba.wakwak.com/~tsuruzoh/Computer/Digicams/exif-e.html   */
19 /* =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- */
20 
21 #include <stdio.h>
22 #include <string.h>
23 #include "defs.h"
24 #include "datadefs.h"
25 #include "maker_datadefs.h"
26 #include "summary.h"
27 #include "maker.h"
28 #include "misc.h"
29 #include "tags.h"
30 #include "maker_extern.h"
31 #include "extern.h"
32 
33 extern struct camera_id fujifilm_model_id[];
34 
35 /* Find the identifying number assigned to known Fujifilm camera      */
36 /* models. This number is used to dispatch print and interpret        */
37 /* routines approopriate to the current image.                        */
38 
39 int
fujifilm_model_number(char * model,char * software)40 fujifilm_model_number(char *model,char *software)
41 {
42     struct camera_id *model_id;
43     int number = NO_MODEL;
44 
45     for(model_id = &fujifilm_model_id[0]; model_id && model_id->name; ++model_id)
46     {
47         if(strncasecmp(model,model_id->name,model_id->namelen) == 0)
48         {
49             number = model_id->id;
50             setnoteversion(model_id->noteversion);
51             setnotetagset(model_id->notetagset);    /* info only      */
52             break;
53         }
54     }
55     return(number);
56 }
57 
58 
59 /* Dispatch a print routine for direct values in Fujifilm cameras,    */
60 /* based upon model                                                   */
61 
62 void
print_fujifilm_makervalue(struct ifd_entry * entry_ptr,int make,int model,char * prefix)63 print_fujifilm_makervalue(struct ifd_entry *entry_ptr,int make,int model,
64                     char *prefix)
65 {
66     int noteversion = 0;
67 
68     if(entry_ptr && (PRINT_VALUE))
69     {
70         noteversion = getnoteversion();
71         switch(noteversion)
72         {
73             case 1:
74                 print_fujifilm1_makervalue(entry_ptr,make,model,prefix);
75                 fujifilm1_interpret_value(entry_ptr);
76                 break;
77             default:
78                 print_value(entry_ptr,PREFIX);
79                 break;
80         }
81     }
82 }
83 
84 /* Model-specific print routine for Fujifilm cameras. This routine is */
85 /* responsible for picking off any direct entry tags which are        */
86 /* peculiar and will not be handled properly by print_value()         */
87 /* (usually UNDEFINED values which fit in the 4-byte entry value). If */
88 /* there are no such entries, this function simply calls              */
89 /* print_value().                                                     */
90 
91 void
print_fujifilm1_makervalue(struct ifd_entry * entry_ptr,int make,int model,char * prefix)92 print_fujifilm1_makervalue(struct ifd_entry *entry_ptr,int make,int model,
93                     char *prefix)
94 {
95     if(entry_ptr && (PRINT_VALUE))
96     {
97         switch(entry_ptr->tag)
98         {
99             default:
100                 print_value(entry_ptr,PREFIX);
101                 break;
102         }
103     }
104 }
105 
106 
107 /* Dispatch a routine to decode and print offset values for Fujifilm  */
108 /* cameras.                                                           */
109 
110 void
print_fujifilm_offset_makervalue(FILE * inptr,unsigned short byteorder,struct ifd_entry * entry_ptr,unsigned long fileoffset_base,struct image_summary * summary_entry,char * parent_name,char * prefix,int indent,int make,int model,int at_offset)111 print_fujifilm_offset_makervalue(FILE *inptr,unsigned short byteorder,
112     struct ifd_entry *entry_ptr,unsigned long fileoffset_base,
113     struct image_summary *summary_entry,char *parent_name,char *prefix,
114     int indent,int make,int model,int at_offset)
115 {
116     int noteversion = 0;
117 
118     if(entry_ptr)
119     {
120         noteversion = getnoteversion();
121         switch(noteversion)
122         {
123             default:
124                 print_generic_offset_makervalue(inptr,byteorder,entry_ptr,
125                                 fileoffset_base,parent_name,prefix,indent,
126                                 make,model,at_offset);
127                 break;
128         }
129     }
130 }
131 
132 
133 
134 /* Fujifilm-specific tagnames for makernotes.                              */
135 
136 char *
maker_fujifilm_tagname(unsigned short tag,int model)137 maker_fujifilm_tagname(unsigned short tag,int model)
138 {
139     char *tagname = (char *)0;
140     int noteversion = 0;
141 
142     /* Should have to do this only once, and only for unrecognized    */
143     /* models. If the model is recognized (or the user has forced a   */
144     /* noteversion) noteversion will already be set.                  */
145     if((noteversion = getnoteversion()) == 0)
146     {
147         /* Only one tagset has been observed so far; it seems         */
148         /* reasonable to default to that tagset (rather than none).   */
149         noteversion = 1;
150         setnoteversion(1);
151     }
152 
153     switch(noteversion)
154     {
155         case 1:
156             tagname = maker_fujifilm1_tagname(tag,model);
157             break;
158         default:
159             break;
160     }
161 
162     /* If no model-specific tag is found, check "generic" tags        */
163     if(tagname == NULL)
164     {
165         switch(tag)
166         {
167             case 0x0e00: tagname = "PrintIM"; break;
168             default: break;
169         }
170     }
171     return(tagname);
172 }
173 
174 char *
maker_fujifilm1_tagname(unsigned short tag,int model)175 maker_fujifilm1_tagname(unsigned short tag,int model)
176 {
177     char *tagname = CNULL;
178 
179     switch(tag)
180     {
181         case 0x0000: tagname = "Version"; break;
182         case 0x1000: tagname = "Quality"; break;
183         case 0x1001: tagname = "Sharpness"; break;
184         case 0x1002: tagname = "WhiteBalance"; break;
185         case 0x1003: tagname = "Color"; break;
186         case 0x1004: tagname = "Tone"; break;
187         case 0x1010: tagname = "FlashMode"; break;
188         case 0x1011: tagname = "FlashStrength"; break;
189         case 0x1020: tagname = "Macro"; break;
190         case 0x1021: tagname = "FocusMode"; break;
191         case 0x1030: tagname = "SlowSync"; break;
192         case 0x1031: tagname = "PictureMode"; break;
193         case 0x1100: tagname = "ContTake-Bracket"; break;
194         case 0x1300: tagname = "BlurWarning"; break;
195         case 0x1301: tagname = "FocusWarning"; break;
196         case 0x1302: tagname = "AEWarning"; break;
197         default: break;
198     }
199     setnotetagset(1);
200     return(tagname);
201 }
202 
203 
204 /* Report the "meaning" of tag values found at offsets in a Fujifilm  */
205 /* MakerNote IFD entry (not at an offset).                            */
206 
207 void
fujifilm1_interpret_value(struct ifd_entry * entry_ptr)208 fujifilm1_interpret_value(struct ifd_entry *entry_ptr)
209 {
210     int chpr = 0;
211 
212     if(entry_ptr && (PRINT_VALUE))
213     {
214         switch(entry_ptr->tag)
215         {
216             case 0x1001:    /* Sharpness */
217                 print_startvalue();
218                 switch(entry_ptr->value)
219                 {
220                     case 1: chpr += printf("Soft"); break;
221                     case 2: chpr += printf("Soft"); break;
222                     case 3: chpr += printf("Normal"); break;
223                     case 4: chpr += printf("Hard"); break;
224                     case 5: chpr += printf("Hard"); break;
225                     default: printred("undefined"); break;
226                 }
227                 print_endvalue();
228                 break;
229             case 0x1002:    /* White Balance */
230                 print_startvalue();
231                 /* I think we're looking at a bit mask here, but I have   */
232                 /* no way to check; this is the way Tachibanaya           */
233                 /* characterizes it.                                      */
234                 switch(entry_ptr->value)
235                 {
236                     case 0: chpr += printf("Auto"); break;
237                     case 256: chpr += printf("Daylight"); break;
238                     case 512: chpr += printf("Cloudy"); break;
239                     case 768:   /* ???? */ printf("DaylightColor-Fluorescent"); break;
240                     case 769:   /* ???? */ printf("DaywhiteColor-Fluorescent"); break;
241                     case 770:   /* ???? */ printf("White-Fluorescent"); break;
242                     case 1024: chpr += printf("Incandescent"); break;
243                     case 3840: chpr += printf("Custom"); break;
244                     default: printred("undefined"); break;
245                 }
246                 print_endvalue();
247                 break;
248             case 0x1003:    /* Color Saturation */
249                 print_startvalue();
250                 switch(entry_ptr->value)
251                 {
252                     case 0: chpr += printf("Standard"); break;
253                     case 256: chpr += printf("High"); break;
254                     case 512: chpr += printf("Low"); break;
255                     default: printred("undefined"); break;
256                 }
257                 print_endvalue();
258                 break;
259             case 0x1004:    /* Tone */
260                 print_startvalue();
261                 switch(entry_ptr->value)
262                 {
263                     case 0: chpr += printf("Standard"); break;
264                     case 256: chpr += printf("High"); break;
265                     case 512: chpr += printf("Low"); break;
266                     default: printred("undefined"); break;
267                 }
268                 print_endvalue();
269                 break;
270             case 0x1010:    /* Flash Mode */
271                 print_startvalue();
272                 switch(entry_ptr->value)
273                 {
274                     case 0: chpr += printf("Auto"); break;
275                     case 1: chpr += printf("On"); break;
276                     case 2: chpr += printf("Off"); break;
277                     case 3: chpr += printf("Redeye"); break;
278                     default: printred("undefined"); break;
279                 }
280                 print_endvalue();
281                 break;
282             case 0x1020:    /* Macro Mode */
283                 print_startvalue();
284                 switch(entry_ptr->value)
285                 {
286                     case 0: chpr += printf("Off"); break;
287                     case 1: chpr += printf("On"); break;
288                     default: printred("undefined"); break;
289                 }
290                 print_endvalue();
291                 break;
292             case 0x1021:    /* Focusing Mode */
293                 print_startvalue();
294                 switch(entry_ptr->value)
295                 {
296                     case 0: chpr += printf("Auto"); break;
297                     case 1: chpr += printf("Manual"); break;
298                     default: printred("undefined"); break;
299                 }
300                 print_endvalue();
301                 break;
302             case 0x1030:    /* Slow Sync */
303                 print_startvalue();
304                 switch(entry_ptr->value)
305                 {
306                     case 0: chpr += printf("Off"); break;
307                     case 1: chpr += printf("On"); break;
308                     default: printred("undefined"); break;
309                 }
310                 print_endvalue();
311                 break;
312             case 0x1031:    /* Picture Mode */
313                 print_startvalue();
314                 switch(entry_ptr->value)
315                 {
316                     case 0: chpr += printf("Auto"); break;
317                     case 1: chpr += printf("Portrait"); break;
318                     case 2: chpr += printf("Landscape"); break;
319                     case 4: chpr += printf("Sports"); break;
320                     case 5: chpr += printf("Night"); break;
321                     case 6: chpr += printf("Program Normal"); break;
322                     case 256: chpr += printf("Aperture Priority"); break;
323                     case 512: chpr += printf("Shutter Priority"); break;
324                     case 768: chpr += printf("Manual"); break;
325                     default: printred("undefined"); }
326                 print_endvalue();
327                 break;
328             case 0x1100:    /* Continuous Take/Bracket */
329                 print_startvalue();
330                 switch(entry_ptr->value)
331                 {
332                     case 0: chpr += printf("Off"); break;
333                     case 1: chpr += printf("On"); break;
334                     default: printred("undefined"); break;
335                 }
336                 print_endvalue();
337                 break;
338             case 0x1300:    /* Blur Warning */
339                 print_startvalue();
340                 switch(entry_ptr->value)
341                 {
342                     case 0: chpr += printf("Ok"); break;
343                     case 1: chpr += printf("Blurred"); break;
344                     default: printred("undefined"); break;
345                 }
346                 print_endvalue();
347                 break;
348             case 0x1301:    /* Focus Warning */
349                 print_startvalue();
350                 switch(entry_ptr->value)
351                 {
352                     case 0: chpr += printf("Ok"); break;
353                     case 1: chpr += printf("Out of focus"); break;
354                     default: printred("undefined"); break;
355                 }
356                 print_endvalue();
357                 break;
358             case 0x1302:    /* AE Warning */
359                 print_startvalue();
360                 switch(entry_ptr->value)
361                 {
362                     case 0: chpr += printf("Ok"); break;
363                     case 1: chpr += printf("Overexposed"); break;
364                     default: printred("undefined"); break;
365                 }
366                 print_endvalue();
367                 break;
368             default:
369                 break;
370         }
371     }
372     setcharsprinted(chpr);
373 }
374