/src/LibRaw/src/utils/read_utils.cpp
Line | Count | Source |
1 | | /* -*- C++ -*- |
2 | | * Copyright 2019-2025 LibRaw LLC (info@libraw.org) |
3 | | * |
4 | | LibRaw uses code from dcraw.c -- Dave Coffin's raw photo decoder, |
5 | | dcraw.c is copyright 1997-2018 by Dave Coffin, dcoffin a cybercom o net. |
6 | | LibRaw do not use RESTRICTED code from dcraw.c |
7 | | |
8 | | LibRaw is free software; you can redistribute it and/or modify |
9 | | it under the terms of the one of two licenses as you choose: |
10 | | |
11 | | 1. GNU LESSER GENERAL PUBLIC LICENSE version 2.1 |
12 | | (See file LICENSE.LGPL provided in LibRaw distribution archive for details). |
13 | | |
14 | | 2. COMMON DEVELOPMENT AND DISTRIBUTION LICENSE (CDDL) Version 1.0 |
15 | | (See file LICENSE.CDDL provided in LibRaw distribution archive for details). |
16 | | |
17 | | */ |
18 | | |
19 | | #include "../../internal/dcraw_defs.h" |
20 | | |
21 | | ushort LibRaw::sget2Rev(uchar *s) // specific to some Canon Makernotes fields, |
22 | | // where they have endian in reverse |
23 | 14.5k | { |
24 | 14.5k | if (order == 0x4d4d) /* "II" means little-endian, and we reverse to "MM" - big |
25 | | endian */ |
26 | 0 | return s[0] | s[1] << 8; |
27 | 14.5k | else /* "MM" means big-endian... */ |
28 | 14.5k | return s[0] << 8 | s[1]; |
29 | 14.5k | } |
30 | | |
31 | | ushort libraw_sget2_static(short _order, uchar *s) |
32 | 409M | { |
33 | 409M | if (_order == 0x4949) /* "II" means little-endian */ |
34 | 302M | return s[0] | s[1] << 8; |
35 | 106M | else /* "MM" means big-endian */ |
36 | 106M | return s[0] << 8 | s[1]; |
37 | 409M | } |
38 | | |
39 | | ushort LibRaw::sget2(uchar *s) |
40 | 407M | { |
41 | 407M | return libraw_sget2_static(order, s); |
42 | 407M | } |
43 | | |
44 | | |
45 | | ushort LibRaw::get2() |
46 | 403M | { |
47 | 403M | uchar str[2] = {0xff, 0xff}; |
48 | 403M | fread(str, 1, 2, ifp); |
49 | 403M | return sget2(str); |
50 | 403M | } |
51 | | |
52 | | unsigned LibRaw::sget4(uchar *s) |
53 | 564M | { |
54 | 564M | return libraw_sget4_static(order, s); |
55 | 564M | } |
56 | | |
57 | | |
58 | | unsigned libraw_sget4_static(short _order, uchar *s) |
59 | 564M | { |
60 | 564M | if (_order == 0x4949) |
61 | 346M | return s[0] | s[1] << 8 | s[2] << 16 | s[3] << 24; |
62 | 217M | else |
63 | 217M | return s[0] << 24 | s[1] << 16 | s[2] << 8 | s[3]; |
64 | 564M | } |
65 | | |
66 | | unsigned LibRaw::get4() |
67 | 563M | { |
68 | 563M | uchar str[4] = {0xff, 0xff, 0xff, 0xff}; |
69 | 563M | fread(str, 1, 4, ifp); |
70 | 563M | return sget4(str); |
71 | 563M | } |
72 | | |
73 | 206k | unsigned LibRaw::getint(int type) { return tagtypeIs(LIBRAW_EXIFTAG_TYPE_SHORT) ? get2() : get4(); } |
74 | | |
75 | | float libraw_int_to_float(int i) |
76 | 65.8M | { |
77 | 65.8M | union { |
78 | 65.8M | int i; |
79 | 65.8M | float f; |
80 | 65.8M | } u; |
81 | 65.8M | u.i = i; |
82 | 65.8M | return u.f; |
83 | 65.8M | } |
84 | | |
85 | 65.8M | float LibRaw::int_to_float(int i) { return libraw_int_to_float(i); } |
86 | | |
87 | | double LibRaw::getreal(int type) |
88 | 66.8M | { |
89 | 66.8M | union { |
90 | 66.8M | char c[8]; |
91 | 66.8M | double d; |
92 | 66.8M | } u, v; |
93 | 66.8M | int i, rev; |
94 | | |
95 | 66.8M | switch (type) |
96 | 66.8M | { |
97 | 45.7k | case LIBRAW_EXIFTAG_TYPE_SHORT: |
98 | 45.7k | return (unsigned short)get2(); |
99 | 63.3k | case LIBRAW_EXIFTAG_TYPE_LONG: |
100 | 63.3k | return (unsigned int)get4(); |
101 | 85.9k | case LIBRAW_EXIFTAG_TYPE_RATIONAL: // (unsigned, unsigned) |
102 | 85.9k | u.d = (unsigned int)get4(); |
103 | 85.9k | v.d = (unsigned int)get4(); |
104 | 85.9k | return u.d / (v.d ? v.d : 1); |
105 | 10.7k | case LIBRAW_EXIFTAG_TYPE_SSHORT: |
106 | 10.7k | return (signed short)get2(); |
107 | 292k | case LIBRAW_EXIFTAG_TYPE_SLONG: |
108 | 292k | return (signed int)get4(); |
109 | 196k | case LIBRAW_EXIFTAG_TYPE_SRATIONAL: // (int, int) |
110 | 196k | u.d = (signed int)get4(); |
111 | 196k | v.d = (signed int)get4(); |
112 | 196k | return u.d / (v.d ? v.d : 1); |
113 | 65.8M | case LIBRAW_EXIFTAG_TYPE_FLOAT: |
114 | 65.8M | return int_to_float(get4()); |
115 | 16.0k | case LIBRAW_EXIFTAG_TYPE_DOUBLE: |
116 | 16.0k | rev = 7 * ((order == 0x4949) == (ntohs(0x1234) == 0x1234)); |
117 | 144k | for (i = 0; i < 8; i++) |
118 | 128k | u.c[i ^ rev] = fgetc(ifp); |
119 | 16.0k | return u.d; |
120 | 272k | default: |
121 | 272k | return fgetc(ifp); |
122 | 66.8M | } |
123 | 66.8M | } |
124 | | |
125 | | double LibRaw::sgetreal(int type, uchar *s) |
126 | 0 | { |
127 | 0 | return libraw_sgetreal_static(order, type, s); |
128 | 0 | } |
129 | | |
130 | | |
131 | | double libraw_sgetreal_static(short _order, int type, uchar *s) |
132 | 0 | { |
133 | 0 | union { |
134 | 0 | char c[8]; |
135 | 0 | double d; |
136 | 0 | } u, v; |
137 | 0 | int i, rev; |
138 | |
|
139 | 0 | switch (type) |
140 | 0 | { |
141 | 0 | case LIBRAW_EXIFTAG_TYPE_SHORT: |
142 | 0 | return (unsigned short) libraw_sget2_static(_order,s); |
143 | 0 | case LIBRAW_EXIFTAG_TYPE_LONG: |
144 | 0 | return (unsigned int)libraw_sget4_static(_order, s); |
145 | 0 | case LIBRAW_EXIFTAG_TYPE_RATIONAL: // (unsigned, unsigned) |
146 | 0 | u.d = (unsigned int)libraw_sget4_static(_order,s); |
147 | 0 | v.d = (unsigned int)libraw_sget4_static(_order,s+4); |
148 | 0 | return u.d / (v.d ? v.d : 1); |
149 | 0 | case LIBRAW_EXIFTAG_TYPE_SSHORT: |
150 | 0 | return (signed short)libraw_sget2_static(_order,s); |
151 | 0 | case LIBRAW_EXIFTAG_TYPE_SLONG: |
152 | 0 | return (signed int) libraw_sget4_static(_order,s); |
153 | 0 | case LIBRAW_EXIFTAG_TYPE_SRATIONAL: // (int, int) |
154 | 0 | u.d = (signed int)libraw_sget4_static(_order,s); |
155 | 0 | v.d = (signed int)libraw_sget4_static(_order,s+4); |
156 | 0 | return u.d / (v.d ? v.d : 1); |
157 | 0 | case LIBRAW_EXIFTAG_TYPE_FLOAT: |
158 | 0 | return libraw_int_to_float(libraw_sget4_static(_order,s)); |
159 | 0 | case LIBRAW_EXIFTAG_TYPE_DOUBLE: |
160 | 0 | rev = 7 * ((_order == 0x4949) == (ntohs(0x1234) == 0x1234)); |
161 | 0 | for (i = 0; i < 8; i++) |
162 | 0 | u.c[i ^ rev] = *(s+i); |
163 | 0 | return u.d; |
164 | 0 | default: |
165 | 0 | return *s; |
166 | 0 | } |
167 | 0 | } |
168 | | |
169 | | |
170 | | void LibRaw::read_shorts(ushort *pixel, unsigned count) |
171 | 6.32M | { |
172 | 6.32M | if ((unsigned)fread(pixel, 2, count, ifp) < count) |
173 | 6.24M | derror(); |
174 | 6.32M | if ((order == 0x4949) == (ntohs(0x1234) == 0x1234)) |
175 | 4.23k | libraw_swab(pixel, count * 2); |
176 | 6.32M | } |