libopenraw  0.3.7
orffile.cpp
1 /*
2  * libopenraw - orffile.cpp
3  *
4  * Copyright (C) 2006-2022 Hubert Figuière
5  *
6  * This library is free software: you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public License
8  * as published by the Free Software Foundation, either version 3 of
9  * the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this library. If not, see
18  * <http://www.gnu.org/licenses/>.
19  */
20 
21 #include <algorithm>
22 #include <cstdint>
23 #include <memory>
24 
25 #include <libopenraw/debug.h>
26 #include <libopenraw/cameraids.h>
27 #include <libopenraw/consts.h>
28 
29 #include "mosaicinfo.hpp"
30 #include "rawdata.hpp"
31 #include "rawfile.hpp"
32 
33 #include "ifdfilecontainer.hpp"
34 #include "makernotedir.hpp"
35 
36 #include "trace.hpp"
37 #include "orffile.hpp"
38 #include "ifd.hpp"
39 #include "ifddir.hpp"
40 #include "ifdentry.hpp"
41 #include "orfcontainer.hpp"
42 #include "olympusdecompressor.hpp"
43 #include "rawfile_private.hpp"
44 #include "io/streamclone.hpp"
45 #include "jfifcontainer.hpp"
46 #include "unpack.hpp"
47 
48 using namespace Debug;
49 
50 namespace OpenRaw {
51 namespace Internals {
52 
53 #define OR_MAKE_OLYMPUS_TYPEID(camid) \
54  OR_MAKE_FILE_TYPEID(OR_TYPEID_VENDOR_OLYMPUS,camid)
55 
56 /* taken from dcraw, by default */
57 static const BuiltinColourMatrix s_matrices[] = {
58  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E1),
59  0,
60  0,
61  { 11846,-4767,-945,-7027,15878,1089,-2699,4122,8311 } },
62  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E10),
63  0,
64  0xffc,
65  { 12745,-4500,-1416,-6062,14542,1580,-1934,2256,6603 } },
66  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E3),
67  0,
68  0xf99,
69  { 9487,-2875,-1115,-7533,15606,2010,-1618,2100,7389 } },
70  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E30),
71  0,
72  0,
73  { 8144, -1861, -1111, -7763, 15894, 1929, -1865, 2542, 7607 } },
74  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E5),
75  0,
76  0,
77  { 11200,-3783,-1325,-4576,12593,2206,-695,1742,7504 } },
78  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E300),
79  0,
80  0,
81  { 7828,-1761,-348,-5788,14071,1830,-2853,4518,6557 } },
82  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E330),
83  0,
84  0,
85  { 8961,-2473,-1084,-7979,15990,2067,-2319,3035,8249 } },
86  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E400),
87  0,
88  0,
89  { 6169,-1483,-21,-7107,14761,2536,-2904,3580,8568 } },
90  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E410),
91  0,
92  0xf6a,
93  { 8856,-2582,-1026,-7761,15766,2082,-2009,2575,7469 } },
94  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E420),
95  0,
96  0,
97  { 8745, -2425, -1095, -7594, 15613, 2073, -1780, 2309, 7416 } },
98  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E450),
99  0,
100  0,
101  { 8745, -2425, -1095, -7594, 15613, 2073, -1780, 2309, 7416 } },
102  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E500),
103  0,
104  0,
105  { 8136,-1968,-299,-5481,13742,1871,-2556,4205,6630 } },
106  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E510),
107  0,
108  0xf6a,
109  { 8785,-2529,-1033,-7639,15624,2112,-1783,2300,7817 } },
110  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E520),
111  0,
112  0,
113  { 8343, -2322, -1020, -7596, 15635, 2048, -1748, 2269, 7287 } },
114  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E600),
115  0,
116  0,
117  { 8453, -2198, -1092, -7609, 15681, 2008, -1725, 2337, 7824 } },
118  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E620),
119  0,
120  0xfaf,
121  { 8453,-2198,-1092,-7609,15681,2008,-1725,2337,7824 } },
122  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_SP350),
123  0,
124  0,
125  { 12078,-4836,-1069,-6671,14306,2578,-786,939,7418 } },
126  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_SP500UZ),
127  0,
128  0xfff,
129  { 9493,-3415,-666,-5211,12334,3260,-1548,2262,6482 } },
130  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_SP510UZ),
131  0,
132  0xffe,
133  { 10593,-3607,-1010,-5881,13127,3084,-1200,1805,6721 } },
134  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_SP550UZ),
135  0,
136  0xffe,
137  { 11597,-4006,-1049,-5432,12799,2957,-1029,1750,6516 } },
138  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_SP565UZ),
139  0,
140  0xffe,
141  { 11856, -4470, -1159, -4814, 12368, 2756, -994, 1780, 5589 } },
142  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_SP570UZ),
143  0,
144  0xffe,
145  { 11522, -4044, -1145, -4737, 12172, 2903, -987, 1829, 6039 } },
146  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EP1),
147  0,
148  0xffd,
149  { 8343,-2050,-1021,-7715,15705,2103,-1831,2380,8235 } },
150  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EP2),
151  0,
152  0xffd,
153  { 8343,-2050,-1021,-7715,15705,2103,-1831,2380,8235 } },
154  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EP3),
155  0,
156  0,
157  { 7575,-2159,-571,-3722,11341,2725,-1434,2819,6271 } },
158  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EP5),
159  0,
160  0,
161  { 8380, -2630, -639, -2887, 10725, 2496, -627, 1427, 5438 } },
162  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EP7),
163  0,
164  0,
165  { 9476, -3182, -765, -2613, 10958, 1893, -449, 1315, 5268 } },
166  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL1),
167  0,
168  0,
169  { 11408,-4289,-1215,-4286,12385,2118,-387,1467,7787 } },
170  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL2),
171  0,
172  0,
173  { 15030,-5552,-1806,-3987,12387,1767,-592,1670,7023 } },
174  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL3),
175  0,
176  0,
177  { 7575,-2159,-571,-3722,11341,2725,-1434,2819,6271 } },
178  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL5),
179  0,
180  0xfcb,
181  { 8380,-2630,-639,-2887,10725,2496,-627,1427,5438 } },
182  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL6),
183  0,
184  0xfcb,
185  { 8380,-2630,-639,-2887,10725,2496,-627,1427,5438 } },
186  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL7),
187  0,
188  0xfcb,
189  { 9197,-3190,-659,-2606,10830,2039,-458,1250,5458 } },
190  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL8),
191  0,
192  0xfcb,
193  { 9197, -3190, -659, -2606, 10830, 2039, -458, 1250, 5458 } },
194  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL9),
195  0,
196  0xfcb,
197  { 8380, -2630, -639, -2887, 10725, 2496, -627, 1427, 5438 } },
198  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL10),
199  0,
200  0xfcb,
201  { 9197, -3190, -659, -2606, 10830, 2039, -458, 1250, 5458 } },
202  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPM1),
203  0,
204  0,
205  { 7575,-2159,-571,-3722,11341,2725,-1434,2819,6271 } },
206  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPM2),
207  0,
208  0,
209  { 8380,-2630,-639,-2887,10725,2496,-627,1427,5438 } },
210  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_XZ1),
211  0,
212  0,
213  { 10901,-4095,-1074,-1141,9208,2293,-62,1417,5158 } },
214  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_XZ10),
215  0,
216  0,
217  { 9777, -3483, -925, -2886, 11297, 1800, -602, 1663, 5134 } },
218  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_XZ2),
219  0,
220  0,
221  { 9777,-3483,-925,-2886,11297,1800,-602,1663,5134 } },
222  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM5),
223  0,
224  0xfe1,
225  { 8380, -2630, -639, -2887, 725, 2496, -627, 1427, 5438 } },
226  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM5II),
227  0,
228  0,
229  { 9422, -3258, -711, -2655, 10898, 2015, -512, 1354, 5512 } },
230  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM5III),
231  0,
232  0,
233  { 11896, -5110, -1076, -3181, 11378, 2048, -519, 1224, 5166 } },
234  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM1),
235  0,
236  0,
237  { 7687, -1984, -606, -4327, 11928, 2721, -1381, 2339, 6452 } },
238  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM1II),
239  0,
240  0,
241  { 9383, -3170, -763, -2457, 10702, 2020, -384, 1236, 5552 } },
242  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM1III),
243  0,
244  0,
245  { 11896, -5110, -1076, -3181, 11378, 2048, -519, 1224, 5166 } },
246  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM10),
247  0,
248  0,
249  { 8380, -2630, -639, -2887, 10725, 2496, -627, 1427, 5438 } },
250  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM10II), // Identical to MarkI
251  0,
252  0,
253  { 8380, -2630, -639, -2887, 10725, 2496, -627, 1427, 5438 } },
254  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM10III),
255  0,
256  0,
257  { 8380, -2630, -639, -2887, 10725, 2496, -627, 1427, 5438 } },
258  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM10IIIS),
259  0,
260  0,
261  { 8380, -2630, -639, -2887, 10725, 2496, -627, 1427, 5438 } },
262  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM10IV),
263  0,
264  0,
265  { 9476, -3182, -765, -2613, 10958, 1893, -449, 1315, 5268 } },
266  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM1X),
267  0,
268  0,
269  { 11896, -5110, -1076, -3181, 11378, 2048, -519, 1224, 5166 } },
270  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_OM1),
271  0,
272  0,
273  { 9488, -3984, -714, -2887, 10945, 2229, -137, 960, 5786 } },
274  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_OM5),
275  0,
276  0,
277  { 11896, -5110, -1076, -3181, 11378, 2048, -519, 1224, 5166 } },
278  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_STYLUS1),
279  0,
280  0,
281  { 8360, -2420, -880, -3928, 12353, 1739, -1381, 2416, 5173 } },
282  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_STYLUS1_1S),
283  0,
284  0,
285  { 8360, -2420, -880, -3928, 12353, 1739, -1381, 2416, 5173 } },
286  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_PEN_F),
287  0,
288  0,
289  { 9476, -3182, -765, -2613, 10958, 1893, -449, 1315, 5268 } },
290  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_SH2),
291  0,
292  0,
293  { 10156, -3425, -1077, -2611, 11177, 1624, -385, 1592, 5080 } },
294  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_TG4),
295  0,
296  0,
297  { 11426, -4159, -1126, -2066, 10678, 1593, -120, 1327, 4998 } },
298  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_TG5),
299  0,
300  0,
301  { 10899, -3833, -1082, -2112, 10736, 1575, -267, 1452, 5269 } },
302  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_TG6),
303  0,
304  0,
305  { 10899, -3833, -1082, -2112, 10736, 1575, -267, 1452, 5269 } },
306  { OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_C5060WZ),
307  0,
308  0,
309  { 10445, -3362, -1307, -7662, 15690, 2058, -1135, 1176, 7602 } },
310  { 0, 0, 0, { 0, 0, 0, 0, 0, 0, 0, 0, 0 } }
311 
312 };
313 
314 const struct IfdFile::camera_ids_t OrfFile::s_def[] = {
315  { "E-1 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E1) },
316  { "E-10 " , OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E10) },
317  { "E-3 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E3) },
318  { "E-30 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E30) },
319  { "E-5 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E5) },
320  { "E-300 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E300) },
321  { "E-330 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E330) },
322  { "E-400 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E400) },
323  { "E-410 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E410) },
324  { "E-420 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E420) },
325  { "E-450 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E450) },
326  { "E-500 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E500) },
327  { "E-510 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E510) },
328  { "E-520 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E520) },
329  { "E-600 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E600) },
330  { "E-620 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_E620) },
331  { "SP350" , OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_SP350) },
332  { "SP500UZ" , OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_SP500UZ) },
333  { "SP510UZ" , OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_SP510UZ) },
334  { "SP550UZ ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_SP550UZ) },
335  { "SP565UZ ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_SP565UZ) },
336  { "SP570UZ ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_SP570UZ) },
337  { "E-P1 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EP1) },
338  { "E-P2 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EP2) },
339  { "E-P3 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EP3) },
340  { "E-P5 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EP5) },
341  { "E-P7 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EP7) },
342  { "E-PL1 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL1) },
343  { "E-PL2 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL2) },
344  { "E-PL3 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL3) },
345  { "E-PL5 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL5) },
346  { "E-PL6 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL6) },
347  { "E-PL7 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL7) },
348  { "E-PL8 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL8) },
349  { "E-PL9 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL9) },
350  { "E-PL10 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPL10) },
351  { "E-PM1 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPM1) },
352  { "E-PM2 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EPM2) },
353  { "XZ-1 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_XZ1) },
354  { "XZ-10 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_XZ10) },
355  { "XZ-2 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_XZ2) },
356  { "E-M5 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM5) },
357  { "E-M5MarkII ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM5II) },
358  { "E-M5MarkIII ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM5III) },
359  { "E-M1 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM1) },
360  { "E-M1MarkII ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM1II) },
361  { "E-M1MarkIII ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM1III) },
362  { "E-M1X ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM1X) },
363  { "E-M10 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM10) },
364  { "E-M10MarkII ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM10II) },
365  { "E-M10 Mark III ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM10III) },
366  { "E-M10MarkIIIS ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM10IIIS) },
367  { "E-M10MarkIV ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_EM10IV) },
368  { "OM-1 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_OM1) },
369  { "OM-5 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_OM5) },
370  { "STYLUS1 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_STYLUS1) },
371  { "STYLUS1,1s ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_STYLUS1_1S) },
372  { "PEN-F ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_PEN_F) },
373  { "SH-2 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_SH2) },
374  { "TG-4 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_TG4) },
375  { "TG-5 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_TG5) },
376  { "TG-6 ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_TG6) },
377  { "C5060WZ", OR_MAKE_OLYMPUS_TYPEID(OR_TYPEID_OLYMPUS_C5060WZ) },
378  { 0, 0 }
379 };
380 
381 RawFile *OrfFile::factory(const IO::Stream::Ptr &s)
382 {
383  return new OrfFile(s);
384 }
385 
386 OrfFile::OrfFile(const IO::Stream::Ptr &s)
387  : IfdFile(s, OR_RAWFILE_TYPE_ORF, false)
388 {
389  _setIdMap(s_def);
390  _setMatrices(s_matrices);
391  m_container = new OrfContainer(m_io, 0);
392 }
393 
394 OrfFile::~OrfFile()
395 {
396 }
397 
398 ::or_error OrfFile::_enumThumbnailSizes(std::vector<uint32_t> &list)
399 {
400  auto err = OR_ERROR_NOT_FOUND;
401 
402  err = IfdFile::_enumThumbnailSizes(list);
403  LOGDBG1("got %lu thumbs\n", (LSIZE)list.size());
404 
405  auto exif = exifIfd();
406  if (!exif) {
407  LOGDBG1("can't get exif\n");
408  return err;
409  }
410 
411  auto makerNote = std::dynamic_pointer_cast<MakerNoteDir>(exif->getMakerNoteIfd(type()));
412  if (!makerNote) {
413  LOGDBG1("can't get makernote\n");
414  return err;
415  }
416 
417  auto e = makerNote->getEntry(ORF_TAG_THUMBNAIL_IMAGE);
418  _addThumbnailFromEntry(e, makerNote->getMnoteOffset(), list);
419 
420  auto ifd = makerNote->getIfdInEntry(ORF_TAG_CAMERA_SETTINGS);
421  if (ifd) {
422  LOGDBG1("CameraSettings %lu\n", (LSIZE)ifd->entries().size());
423  uint32_t is_valid = ifd->getValue<uint32_t>(ORF_TAG_CS_PREVIEW_IMAGE_VALID).value_or(0);
424  if (is_valid) {
425  uint32_t start =
426  ifd->getValue<uint32_t>(ORF_TAG_CS_PREVIEW_IMAGE_START).value_or(0);
427  if (start) {
428  start += makerNote->getMnoteOffset();
429  }
430  uint32_t len = ifd->getValue<uint32_t>(ORF_TAG_CS_PREVIEW_IMAGE_LENGTH).value_or(0);
431  LOGDBG1("is_valid %u, start %u len %u\n", is_valid, start, len);
432 
433  // if either value is zero we consider it is wrong.
434  if (start != 0 && len != 0) {
435  err = _addThumbnailFromStream(start, len, list);
436  } else {
437  err = OR_ERROR_NOT_FOUND;
438  }
439  }
440  }
441 
442  return err;
443 }
444 
445 ::or_error OrfFile::_getRawData(RawData & data, uint32_t options)
446 {
447  ::or_error err;
448  const IfdDir::Ref & _cfaIfd = cfaIfd();
449  err = _getRawDataFromDir(data, _cfaIfd);
450  if(err == OR_ERROR_NONE) {
451  // ORF files seems to be marked as uncompressed even if they are.
452  uint32_t x = data.width();
453  uint32_t y = data.height();
454  uint32_t compression = 0;
455  if(data.size() < x * y * 2) {
456  compression = IFD::COMPRESS_OLYMPUS;
457  data.setCompression(IFD::COMPRESS_OLYMPUS);
459  }
460  else {
461  compression = data.compression();
462  }
463  switch(compression) {
465  if((options & OR_OPTIONS_DONT_DECOMPRESS) == 0) {
466  err = decompress(x, y, data);
467  }
468  break;
469  default:
470  break;
471  }
472  }
473  return err;
474 }
475 
476 ::or_error OrfFile::decompress(uint32_t x, uint32_t y, RawData& data)
477 {
478  // packed bits
479  if (data.size() == (y * ((x * 12 / 8) + ((x + 2) / 10)))) {
480  // unpack with control le version of NikonPack
481  LOGDBG1("ORF: unpack with control\n");
482  RawDataPtr output(new RawData);
483 
484  uint32_t current_offset = 0;
485  Unpack unpack(x, IFD::COMPRESS_OLYMPUS);
486  const size_t blocksize = unpack.block_size();
487  LOGDBG1("Block size = %lu\n", (LSIZE)blocksize);
488  LOGDBG1("dimensions (x, y) %u, %u\n", x, y);
489  auto pdata = (uint8_t*)data.data();
490 
491  size_t outsize = x * y * 2;
492  uint16_t* outdata = (uint16_t*)output->allocData(outsize);
493  LOGDBG1("offset of RAW data = %u\n", current_offset);
494  do {
495 
496  size_t out;
497  auto ret = unpack.unpack_le12to16(outdata, outsize,
498  pdata,
499  blocksize, out);
500  pdata += blocksize;
501  current_offset += blocksize;
502  outdata += out / 2;
503  outsize -= out;
504  if (ret != OR_ERROR_NONE) {
505  break;
506  }
507  } while(current_offset < data.size());
508 
509  output->setCfaPatternType(data.mosaicInfo()->patternType());
510  output->setPhotometricInterpretation(data.getPhotometricInterpretation());
511  data.swap(*output);
512  data.setBpc(12);
513  data.setWhiteLevel((1 << 12) - 1);
514  } else {
515 
516  LOGDBG1("ORF: decompress\n");
517  // Otherwise it's compressed.
518  OlympusDecompressor decomp((const uint8_t*)data.data(),
519  data.size(), m_container, x, y);
520  RawDataPtr dData = decomp.decompress();
521  if (dData) {
522  dData->setCfaPatternType(data.mosaicInfo()->patternType());
523  dData->setPhotometricInterpretation(data.getPhotometricInterpretation());
524  data.swap(*dData);
525  }
526  }
527 
529  data.setDimensions(x, y);
530  return OR_ERROR_NONE;
531 }
532 
533 }
534 }
535 /*
536  Local Variables:
537  mode:c++
538  c-file-style:"stroustrup"
539  c-file-offsets:((innamespace . 0))
540  indent-tabs-mode:nil
541  fill-column:80
542  End:
543 */
void setDataType(DataType _type)
Set the data type.
Definition: bitmapdata.cpp:91
uint32_t width() const
Width of the image data.
Definition: bitmapdata.cpp:137
uint32_t height() const
Height of the image data.
Definition: bitmapdata.cpp:142
void setBpc(uint32_t _bpc)
Set bit per channel.
Definition: bitmapdata.cpp:152
size_t size() const
Get the size of the data.
Definition: bitmapdata.cpp:120
std::shared_ptr< Stream > Ptr
Definition: stream.hpp:47
std::shared_ptr< IfdDir > Ref
Shared ptr of an IfdDir.
Definition: ifddir.hpp:56
::or_error _addThumbnailFromStream(uint32_t offset, uint32_t len, std::vector< uint32_t > &list)
Add a thumbnail from a stream.
Definition: ifdfile.cpp:133
IO::Stream::Ptr m_io
Definition: ifdfile.hpp:106
virtual ::or_error _enumThumbnailSizes(std::vector< uint32_t > &list) override
List the thumbnails in the IFD.
Definition: ifdfile.cpp:173
IfdFileContainer * m_container
Definition: ifdfile.hpp:107
::or_error _getRawDataFromDir(RawData &data, const IfdDir::Ref &dir)
Load the compressed raw data from a standard location in an IFD.
Definition: ifdfile.cpp:533
::or_error _addThumbnailFromEntry(const IfdEntry::Ref &e, off_t offset, std::vector< uint32_t > &list)
Add the thumbnail found in the IfdEntry.
Definition: ifdfile.cpp:158
::or_cfa_pattern patternType() const
Definition: mosaicinfo.cpp:199
Represent camera raw data.
Definition: rawdata.hpp:38
void swap(RawData &with)
Definition: rawdata.cpp:282
const MosaicInfo * mosaicInfo() const
Definition: rawdata.cpp:335
virtual void setDimensions(uint32_t x, uint32_t y) override
Set the pixel dimensions of the bitmap.
Definition: rawdata.cpp:297
RAW file.
Definition: rawfile.hpp:66
Internals::IfdDir::Ref exifIfd()
Get the Exif IFD.
Definition: rawfile.cpp:715
Internals::IfdDir::Ref cfaIfd()
Get the IFD containing the CFA.
Definition: rawfile.cpp:696
Type type() const
Accessor for the type.
Definition: rawfile.cpp:375
or_error
Error codes returned by libopenraw.
Definition: consts.h:42
@ OR_DATA_TYPE_COMPRESSED_RAW
Definition: consts.h:88
@ OR_DATA_TYPE_RAW
Definition: consts.h:87
@ OR_OPTIONS_DONT_DECOMPRESS
Definition: consts.h:114
@ OR_RAWFILE_TYPE_ORF
Definition: consts.h:67
@ OR_ERROR_NONE
Definition: consts.h:43
@ OR_ERROR_NOT_FOUND
Definition: consts.h:48
Global namespace for libopenraw.
Definition: arwfile.cpp:29
::or_error _enumThumbnailSizes(std::vector< uint32_t > &list) override
List the thumbnails in the IFD.
Definition: orffile.cpp:398
virtual ::or_error _getRawData(RawData &data, uint32_t options) override
Get the RAW data.
Definition: orffile.cpp:445