28 #include "rawdata.hpp" 29 #include "olympusdecompressor.hpp" 30 #include "bititerator.hpp" 35 static void decompressOlympus(
const uint8_t* buffer,
size_t size, uint8_t* data,
36 uint32_t w, uint32_t h);
39 static void decompressOlympus(
const uint8_t* buffer,
size_t size, uint8_t* data,
40 uint32_t w, uint32_t h)
42 int nbits, sign, low, high, i, wo0, n, nw0, wo1, nw1;
43 int acarry0[3], acarry1[3], pred, diff;
50 for (i = 0; i < 4096; i++) {
52 for (high = 0; high < 12; high++) {
53 if ((b >> (11 - high)) & 1) {
59 wo0 = nw0 = wo1 = nw1 = 0;
62 BitIterator bits(buffer, size - 7);
64 for (uint32_t y = 0; y < h; y++) {
65 memset(acarry0, 0,
sizeof acarry0);
66 memset(acarry1, 0,
sizeof acarry1);
67 uint16_t* dest = (uint16_t*)&data[y * pitch];
68 for (uint32_t x = 0; x < w; x++) {
71 i = 2 * (acarry0[2] < 3);
72 for (nbits = 2 + i; (uint16_t)acarry0[0] >> (nbits + i); nbits++) {
75 uint32_t b = bits.peek(15);
76 sign = (b >> 14) * -1;
78 high = bittable[b & 4095];
80 bits.skip(std::min(12 + 3, high + 1 + 3));
83 high = bits.get(16 - nbits) >> 1;
86 acarry0[0] = (high << nbits) | bits.get(nbits);
87 diff = (acarry0[0] ^ sign) + acarry0[1];
88 acarry0[1] = (diff * 3 + acarry0[1]) >> 5;
89 acarry0[2] = acarry0[0] > 16 ? 0 : acarry0[2] + 1;
97 pred = dest[-pitch + ((int)x)];
100 dest[x] = pred + ((diff << 2) | low);
104 n = dest[-pitch + ((int)x)];
105 if (((wo0 < nw0) & (nw0 < n)) | ((n < nw0) & (nw0 < wo0))) {
106 if (abs(wo0 - nw0) > 32 || abs(n - nw0) > 32) {
107 pred = wo0 + n - nw0;
109 pred = (wo0 + n) >> 1;
112 pred = abs(wo0 - nw0) > abs(n - nw0) ? wo0 : n;
115 dest[x] = pred + ((diff << 2) | low);
126 i = 2 * (acarry1[2] < 3);
127 for (nbits = 2 + i; (uint16_t)acarry1[0] >> (nbits + i); nbits++) {
130 sign = (b >> 14) * -1;
132 high = bittable[b & 4095];
134 bits.skip(std::min(12 + 3, high + 1 + 3));
137 high = bits.get(16 - nbits) >> 1;
140 acarry1[0] = (high << nbits) | bits.get(nbits);
141 diff = (acarry1[0] ^ sign) + acarry1[1];
142 acarry1[1] = (diff * 3 + acarry1[1]) >> 5;
143 acarry1[2] = acarry1[0] > 16 ? 0 : acarry1[2] + 1;
145 if (y < 2 || x < 2) {
146 if (y < 2 && x < 2) {
151 pred = dest[-pitch + ((int)x)];
154 dest[x] = pred + ((diff << 2) | low);
158 n = dest[-pitch + ((int)x)];
159 if (((wo1 < nw1) & (nw1 < n)) | ((n < nw1) & (nw1 < wo1))) {
160 if (abs(wo1 - nw1) > 32 || abs(n - nw1) > 32) {
161 pred = wo1 + n - nw1;
163 pred = (wo1 + n) >> 1;
166 pred = abs(wo1 - nw1) > abs(n - nw1) ? wo1 : n;
169 dest[x] = pred + ((diff << 2) | low);
182 RawDataPtr output(
new RawData);
184 output->allocData(m_w * m_h * 2);
185 decompressOlympus(m_buffer, m_size, (uint8_t*)output->data(), m_w, m_h);
189 output->setWhiteLevel((1 << 12) - 1);
CIFF is the container for CRW files. It is an attempt from Canon to make this a standard. I guess it failed.
virtual RawDataPtr decompress() override