1 /*
2  * Copyright 2012,2016 Dmitry Timoshkov
3  *
4  * This library is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU Lesser General Public
6  * License as published by the Free Software Foundation; either
7  * version 2.1 of the License, or (at your option) any later version.
8  *
9  * This library is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12  * Lesser General Public License for more details.
13  *
14  * You should have received a copy of the GNU Lesser General Public
15  * License along with this library; if not, write to the Free Software
16  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
17  */
18 
19 #include <math.h>
20 #include <stdarg.h>
21 #include <stdio.h>
22 
23 #define COBJMACROS
24 
25 #include "windef.h"
26 #include "wincodec.h"
27 #include "wine/test.h"
28 
29 #define EXPECT_REF(obj,ref) _expect_ref((IUnknown*)obj, ref, __LINE__)
30 static void _expect_ref(IUnknown* obj, ULONG ref, int line)
31 {
32     ULONG rc;
33     IUnknown_AddRef(obj);
34     rc = IUnknown_Release(obj);
35     ok_(__FILE__,line)(rc == ref, "expected refcount %d, got %d\n", ref, rc);
36 }
37 
38 #define IFD_BYTE 1
39 #define IFD_ASCII 2
40 #define IFD_SHORT 3
41 #define IFD_LONG 4
42 #define IFD_RATIONAL 5
43 #define IFD_SBYTE 6
44 #define IFD_UNDEFINED 7
45 #define IFD_SSHORT 8
46 #define IFD_SLONG 9
47 #define IFD_SRATIONAL 10
48 #define IFD_FLOAT 11
49 #define IFD_DOUBLE 12
50 
51 #include "pshpack2.h"
52 struct IFD_entry
53 {
54     SHORT id;
55     SHORT type;
56     ULONG count;
57     LONG  value;
58 };
59 
60 struct IFD_rational
61 {
62     LONG numerator;
63     LONG denominator;
64 };
65 
66 static const struct tiff_1bpp_data
67 {
68     USHORT byte_order;
69     USHORT version;
70     ULONG  dir_offset;
71     USHORT number_of_entries;
72     struct IFD_entry entry[13];
73     ULONG next_IFD;
74     struct IFD_rational res;
75     BYTE pixel_data[4];
76 } tiff_1bpp_data =
77 {
78 #ifdef WORDS_BIGENDIAN
79     'M' | 'M' << 8,
80 #else
81     'I' | 'I' << 8,
82 #endif
83     42,
84     FIELD_OFFSET(struct tiff_1bpp_data, number_of_entries),
85     13,
86     {
87         { 0xff, IFD_SHORT, 1, 0 }, /* SUBFILETYPE */
88         { 0x100, IFD_LONG, 1, 1 }, /* IMAGEWIDTH */
89         { 0x101, IFD_LONG, 1, 1 }, /* IMAGELENGTH */
90         { 0x102, IFD_SHORT, 1, 1 }, /* BITSPERSAMPLE */
91         { 0x103, IFD_SHORT, 1, 1 }, /* COMPRESSION: XP doesn't accept IFD_LONG here */
92         { 0x106, IFD_SHORT, 1, 1 }, /* PHOTOMETRIC */
93         { 0x111, IFD_LONG, 1, FIELD_OFFSET(struct tiff_1bpp_data, pixel_data) }, /* STRIPOFFSETS */
94         { 0x115, IFD_SHORT, 1, 1 }, /* SAMPLESPERPIXEL */
95         { 0x116, IFD_LONG, 1, 1 }, /* ROWSPERSTRIP */
96         { 0x117, IFD_LONG, 1, 1 }, /* STRIPBYTECOUNT */
97         { 0x11a, IFD_RATIONAL, 1, FIELD_OFFSET(struct tiff_1bpp_data, res) }, /* XRESOLUTION */
98         { 0x11b, IFD_RATIONAL, 1, FIELD_OFFSET(struct tiff_1bpp_data, res) }, /* YRESOLUTION */
99         { 0x128, IFD_SHORT, 1, 2 }, /* RESOLUTIONUNIT */
100     },
101     0,
102     { 900, 3 },
103     { 0x11, 0x22, 0x33, 0 }
104 };
105 
106 static const struct tiff_8bpp_alpha
107 {
108     USHORT byte_order;
109     USHORT version;
110     ULONG  dir_offset;
111     USHORT number_of_entries;
112     struct IFD_entry entry[15];
113     ULONG next_IFD;
114     struct IFD_rational res;
115     BYTE pixel_data[8];
116 } tiff_8bpp_alpha =
117 {
118 #ifdef WORDS_BIGENDIAN
119     'M' | 'M' << 8,
120 #else
121     'I' | 'I' << 8,
122 #endif
123     42,
124     FIELD_OFFSET(struct tiff_8bpp_alpha, number_of_entries),
125     15,
126     {
127         { 0xff, IFD_SHORT, 1, 0 }, /* SUBFILETYPE */
128         { 0x100, IFD_LONG, 1, 2 }, /* IMAGEWIDTH */
129         { 0x101, IFD_LONG, 1, 2 }, /* IMAGELENGTH */
130         { 0x102, IFD_SHORT, 2, MAKELONG(8, 8) }, /* BITSPERSAMPLE */
131         { 0x103, IFD_SHORT, 1, 1 }, /* COMPRESSION: XP doesn't accept IFD_LONG here */
132         { 0x106, IFD_SHORT, 1, 1 }, /* PHOTOMETRIC */
133         { 0x111, IFD_LONG, 1, FIELD_OFFSET(struct tiff_8bpp_alpha, pixel_data) }, /* STRIPOFFSETS */
134         { 0x115, IFD_SHORT, 1, 2 }, /* SAMPLESPERPIXEL */
135         { 0x116, IFD_LONG, 1, 2 }, /* ROWSPERSTRIP */
136         { 0x117, IFD_LONG, 1, 8 }, /* STRIPBYTECOUNT */
137         { 0x11a, IFD_RATIONAL, 1, FIELD_OFFSET(struct tiff_8bpp_alpha, res) }, /* XRESOLUTION */
138         { 0x11b, IFD_RATIONAL, 1, FIELD_OFFSET(struct tiff_8bpp_alpha, res) }, /* YRESOLUTION */
139         { 0x11c, IFD_SHORT, 1, 1 }, /* PLANARCONFIGURATION */
140         { 0x128, IFD_SHORT, 1, 2 }, /* RESOLUTIONUNIT */
141         { 0x152, IFD_SHORT, 1, 1 } /* EXTRASAMPLES: 1 - Associated alpha with pre-multiplied color */
142     },
143     0,
144     { 96, 1 },
145     { 0x11,0x22,0x33,0x44,0x55,0x66,0x77,0x88 }
146 };
147 
148 static const struct tiff_8bpp_data
149 {
150     USHORT byte_order;
151     USHORT version;
152     ULONG  dir_offset;
153     USHORT number_of_entries;
154     struct IFD_entry entry[14];
155     ULONG next_IFD;
156     struct IFD_rational res;
157     short palette_data[3][256];
158     BYTE pixel_data[4];
159 } tiff_8bpp_data =
160 {
161 #ifdef WORDS_BIGENDIAN
162     'M' | 'M' << 8,
163 #else
164     'I' | 'I' << 8,
165 #endif
166     42,
167     FIELD_OFFSET(struct tiff_8bpp_data, number_of_entries),
168     14,
169     {
170         { 0xff, IFD_SHORT, 1, 0 }, /* SUBFILETYPE */
171         { 0x100, IFD_LONG, 1, 4 }, /* IMAGEWIDTH */
172         { 0x101, IFD_LONG, 1, 1 }, /* IMAGELENGTH */
173         { 0x102, IFD_SHORT, 1, 8 }, /* BITSPERSAMPLE: XP doesn't accept IFD_LONG here */
174         { 0x103, IFD_SHORT, 1, 1 }, /* COMPRESSION: XP doesn't accept IFD_LONG here */
175         { 0x106, IFD_SHORT, 1, 3 }, /* PHOTOMETRIC */
176         { 0x111, IFD_LONG, 1, FIELD_OFFSET(struct tiff_8bpp_data, pixel_data) }, /* STRIPOFFSETS */
177         { 0x115, IFD_SHORT, 1, 1 }, /* SAMPLESPERPIXEL */
178         { 0x116, IFD_LONG, 1, 1 }, /* ROWSPERSTRIP */
179         { 0x117, IFD_LONG, 1, 1 }, /* STRIPBYTECOUNT */
180         { 0x11a, IFD_RATIONAL, 1, FIELD_OFFSET(struct tiff_8bpp_data, res) },
181         { 0x11b, IFD_RATIONAL, 1, FIELD_OFFSET(struct tiff_8bpp_data, res) },
182         { 0x128, IFD_SHORT, 1, 2 }, /* RESOLUTIONUNIT */
183         { 0x140, IFD_SHORT, 256*3, FIELD_OFFSET(struct tiff_8bpp_data, palette_data) } /* COLORMAP */
184     },
185     0,
186     { 96, 1 },
187     { { 0 } },
188     { 0,1,2,3 }
189 };
190 
191 static const struct tiff_resolution_test_data
192 {
193     struct IFD_rational resx;
194     struct IFD_rational resy;
195     LONG resolution_unit;
196     double expected_dpi_x;
197     double expected_dpi_y;
198     /* if != 0: values for different behavior of some Windows versions */
199     double broken_dpi_x;
200     double broken_dpi_y;
201 } tiff_resolution_test_data[] =
202 {
203     { { 100, 1 }, {  50, 1 }, 0, 100.0,  50.0,     0,      0  }, /* invalid resolution unit */
204     { {  50, 1 }, { 100, 1 }, 0,  50.0, 100.0,     0,      0  },
205 
206     { { 100, 1 }, {  50, 1 }, 1, 100.0,  50.0,     0,      0  }, /* RESUNIT_NONE */
207     { {  50, 1 }, { 100, 1 }, 1,  50.0, 100.0,     0,      0  },
208 
209     { {  49, 1 }, {  49, 1 }, 2,  49.0,  49.0,     0,      0  }, /* same resolution for both X and Y */
210     { {  33, 1 }, {  55, 1 }, 2,  33.0,  55.0,     0,      0  }, /* different resolutions for X and Y */
211     { {  50, 2 }, {  66, 3 }, 2,  25.0,  22.0,     0,      0  }, /* denominator != 1 */
212 
213     { { 100, 1 }, { 200, 1 }, 3, 254.0, 508.0,     0,      0  }, /* unit = centimeters */
214 
215     /* XP and Server 2003 do not discard both resolution values if only one of them is invalid */
216     { {   0, 1 }, {  29, 1 }, 2,  96.0,  96.0,     0,   29.0  }, /* resolution 0 */
217     { {  58, 1 }, {  29, 0 }, 2,  96.0,  96.0,  58.0,      0  }, /* denominator 0 (division by zero) */
218 
219     /* XP and Server 2003 return 96 dots per centimeter (= 243.84 dpi) as fallback value */
220     { {   0, 1 }, { 100, 1 }, 3,  96.0,  96.0, 243.84, 254.0  }, /* resolution 0 and unit = centimeters */
221     { {  50, 1 }, {  72, 0 }, 3,  96.0,  96.0, 127.0,  243.84 }  /* denominator 0 and unit = centimeters */
222 };
223 
224 static struct tiff_resolution_image_data
225 {
226     USHORT byte_order;
227     USHORT version;
228     ULONG dir_offset;
229     USHORT number_of_entries;
230     struct IFD_entry entry[13];
231     ULONG next_IFD;
232     struct IFD_rational resx;
233     struct IFD_rational resy;
234     BYTE pixel_data[4];
235 } tiff_resolution_image_data =
236 {
237 #ifdef WORDS_BIGENDIAN
238     'M' | 'M' << 8,
239 #else
240     'I' | 'I' << 8,
241 #endif
242     42,
243     FIELD_OFFSET(struct tiff_resolution_image_data, number_of_entries),
244     13,
245     {
246         { 0xff, IFD_SHORT, 1, 0 }, /* SUBFILETYPE */
247         { 0x100, IFD_LONG, 1, 1 }, /* IMAGEWIDTH */
248         { 0x101, IFD_LONG, 1, 1 }, /* IMAGELENGTH */
249         { 0x102, IFD_SHORT, 1, 1 }, /* BITSPERSAMPLE */
250         { 0x103, IFD_SHORT, 1, 1 }, /* COMPRESSION: XP doesn't accept IFD_LONG here */
251         { 0x106, IFD_SHORT, 1, 1 }, /* PHOTOMETRIC */
252         { 0x111, IFD_LONG, 1, FIELD_OFFSET(struct tiff_resolution_image_data, pixel_data) }, /* STRIPOFFSETS */
253         { 0x115, IFD_SHORT, 1, 1 }, /* SAMPLESPERPIXEL */
254         { 0x116, IFD_LONG, 1, 1 }, /* ROWSPERSTRIP */
255         { 0x117, IFD_LONG, 1, 1 }, /* STRIPBYTECOUNT */
256         { 0x11a, IFD_RATIONAL, 1, FIELD_OFFSET(struct tiff_resolution_image_data, resx) }, /* XRESOLUTION */
257         { 0x11b, IFD_RATIONAL, 1, FIELD_OFFSET(struct tiff_resolution_image_data, resy) }, /* YRESOLUTION */
258         { 0x128, IFD_SHORT, 1, 1 }, /* RESOLUTIONUNIT -- value will be filled with test data */
259     },
260     0,
261     { 72, 1 }, /* value will be filled with test data */
262     { 72, 1 }, /* value will be filled with test data */
263     { 0x11, 0x22, 0x33, 0 }
264 };
265 
266 static const struct tiff_24bpp_data
267 {
268     USHORT byte_order;
269     USHORT version;
270     ULONG  dir_offset;
271     USHORT number_of_entries;
272     struct IFD_entry entry[13];
273     ULONG next_IFD;
274     struct IFD_rational res;
275     BYTE pixel_data[3];
276 } tiff_24bpp_data =
277 {
278 #ifdef WORDS_BIGENDIAN
279     'M' | 'M' << 8,
280 #else
281     'I' | 'I' << 8,
282 #endif
283     42,
284     FIELD_OFFSET(struct tiff_1bpp_data, number_of_entries),
285     13,
286     {
287         { 0xff, IFD_SHORT, 1, 0 }, /* SUBFILETYPE */
288         { 0x100, IFD_LONG, 1, 1 }, /* IMAGEWIDTH */
289         { 0x101, IFD_LONG, 1, 1 }, /* IMAGELENGTH */
290         { 0x102, IFD_SHORT, 1, 8 }, /* BITSPERSAMPLE */
291         { 0x103, IFD_SHORT, 1, 1 }, /* COMPRESSION: XP doesn't accept IFD_LONG here */
292         { 0x106, IFD_SHORT, 1, 2 }, /* PHOTOMETRIC */
293         { 0x111, IFD_LONG, 1, FIELD_OFFSET(struct tiff_24bpp_data, pixel_data) }, /* STRIPOFFSETS */
294         { 0x115, IFD_SHORT, 1, 3 }, /* SAMPLESPERPIXEL */
295         { 0x116, IFD_LONG, 1, 1 }, /* ROWSPERSTRIP */
296         { 0x117, IFD_LONG, 1, 3 }, /* STRIPBYTECOUNT */
297         { 0x11a, IFD_RATIONAL, 1, FIELD_OFFSET(struct tiff_24bpp_data, res) }, /* XRESOLUTION */
298         { 0x11b, IFD_RATIONAL, 1, FIELD_OFFSET(struct tiff_24bpp_data, res) }, /* YRESOLUTION */
299         { 0x128, IFD_SHORT, 1, 2 }, /* RESOLUTIONUNIT */
300     },
301     0,
302     { 900, 3 },
303     { 0x11, 0x22, 0x33 }
304 };
305 #include "poppack.h"
306 
307 static IWICImagingFactory *factory;
308 
309 static IStream *create_stream(const void *data, int data_size)
310 {
311     HRESULT hr;
312     IStream *stream;
313     HGLOBAL hdata;
314     void *locked_data;
315 
316     hdata = GlobalAlloc(GMEM_MOVEABLE, data_size);
317     ok(hdata != 0, "GlobalAlloc failed\n");
318     if (!hdata) return NULL;
319 
320     locked_data = GlobalLock(hdata);
321     memcpy(locked_data, data, data_size);
322     GlobalUnlock(hdata);
323 
324     hr = CreateStreamOnHGlobal(hdata, TRUE, &stream);
325     ok(hr == S_OK, "CreateStreamOnHGlobal failed, hr=%x\n", hr);
326 
327     return stream;
328 }
329 
330 static HRESULT create_decoder(const void *image_data, UINT image_size, IWICBitmapDecoder **decoder)
331 {
332     HGLOBAL hmem;
333     BYTE *data;
334     HRESULT hr;
335     IStream *stream;
336     GUID format;
337     LONG refcount;
338 
339     *decoder = NULL;
340 
341     hmem = GlobalAlloc(0, image_size);
342     data = GlobalLock(hmem);
343     memcpy(data, image_data, image_size);
344     GlobalUnlock(hmem);
345 
346     hr = CreateStreamOnHGlobal(hmem, TRUE, &stream);
347     ok(hr == S_OK, "CreateStreamOnHGlobal error %#x\n", hr);
348 
349     hr = IWICImagingFactory_CreateDecoderFromStream(factory, stream, NULL, 0, decoder);
350     if (hr == S_OK)
351     {
352         hr = IWICBitmapDecoder_GetContainerFormat(*decoder, &format);
353         ok(hr == S_OK, "GetContainerFormat error %#x\n", hr);
354         ok(IsEqualGUID(&format, &GUID_ContainerFormatTiff),
355            "wrong container format %s\n", wine_dbgstr_guid(&format));
356 
357         refcount = IStream_Release(stream);
358         ok(refcount > 0, "expected stream refcount > 0\n");
359     }
360 
361     return hr;
362 }
363 
364 static HRESULT get_pixelformat_info(const GUID *format, UINT *bpp, UINT *channels, BOOL *trasparency)
365 {
366     HRESULT hr;
367     IWICComponentInfo *info;
368     IWICPixelFormatInfo2 *formatinfo;
369 
370     hr = IWICImagingFactory_CreateComponentInfo(factory, format, &info);
371     ok(hr == S_OK, "CreateComponentInfo(%s) error %#x\n", wine_dbgstr_guid(format), hr);
372     if (hr == S_OK)
373     {
374         hr = IWICComponentInfo_QueryInterface(info, &IID_IWICPixelFormatInfo2, (void **)&formatinfo);
375         if (hr == S_OK)
376         {
377             hr = IWICPixelFormatInfo2_SupportsTransparency(formatinfo, trasparency);
378             ok(hr == S_OK, "SupportsTransparency error %#x\n", hr);
379             IWICPixelFormatInfo2_Release(formatinfo);
380         }
381         hr = IWICComponentInfo_QueryInterface(info, &IID_IWICPixelFormatInfo, (void **)&formatinfo);
382         if (hr == S_OK)
383         {
384             hr = IWICPixelFormatInfo2_GetBitsPerPixel(formatinfo, bpp);
385             ok(hr == S_OK, "GetBitsPerPixel error %#x\n", hr);
386             hr = IWICPixelFormatInfo2_GetChannelCount(formatinfo, channels);
387             ok(hr == S_OK, "GetChannelCount error %#x\n", hr);
388             IWICPixelFormatInfo2_Release(formatinfo);
389         }
390         IWICComponentInfo_Release(info);
391     }
392     return hr;
393 }
394 
395 static void dump_tiff(void *buf)
396 {
397     UINT count, i;
398     struct tiff_1bpp_data *tiff;
399     struct IFD_entry *tag;
400 
401     tiff = buf;
402     count = *(short *)((char *)tiff + tiff->dir_offset);
403     tag = (struct IFD_entry *)((char *)tiff + tiff->dir_offset + sizeof(short));
404 
405     for (i = 0; i < count; i++)
406     {
407         printf("tag %u: id %04x, type %04x, count %u, value %d",
408                 i, tag[i].id, tag[i].type, tag[i].count, tag[i].value);
409         if (tag[i].id == 0x102 && tag[i].count > 2)
410         {
411             short *bps = (short *)((char *)tiff + tag[i].value);
412             printf(" (%d,%d,%d,%d)\n", bps[0], bps[1], bps[2], bps[3]);
413         }
414         else
415             printf("\n");
416     }
417 }
418 
419 static void test_tiff_1bpp_palette(void)
420 {
421     HRESULT hr;
422     IWICBitmapDecoder *decoder;
423     IWICBitmapFrameDecode *frame;
424     IWICPalette *palette;
425     GUID format;
426 
427     hr = create_decoder(&tiff_1bpp_data, sizeof(tiff_1bpp_data), &decoder);
428     ok(hr == S_OK, "Failed to load TIFF image data %#x\n", hr);
429     if (hr != S_OK) return;
430 
431     hr = IWICBitmapDecoder_GetFrame(decoder, 0, &frame);
432     ok(hr == S_OK, "GetFrame error %#x\n", hr);
433 
434     hr = IWICBitmapFrameDecode_GetPixelFormat(frame, &format);
435     ok(hr == S_OK, "GetPixelFormat error %#x\n", hr);
436     ok(IsEqualGUID(&format, &GUID_WICPixelFormatBlackWhite),
437        "got wrong format %s\n", wine_dbgstr_guid(&format));
438 
439     hr = IWICImagingFactory_CreatePalette(factory, &palette);
440     ok(hr == S_OK, "CreatePalette error %#x\n", hr);
441     hr = IWICBitmapFrameDecode_CopyPalette(frame, palette);
442     ok(hr == WINCODEC_ERR_PALETTEUNAVAILABLE,
443        "expected WINCODEC_ERR_PALETTEUNAVAILABLE, got %#x\n", hr);
444 
445     IWICPalette_Release(palette);
446     IWICBitmapFrameDecode_Release(frame);
447     IWICBitmapDecoder_Release(decoder);
448 }
449 
450 static void test_QueryCapability(void)
451 {
452     HRESULT hr;
453     IStream *stream;
454     IWICBitmapDecoder *decoder;
455     IWICBitmapFrameDecode *frame;
456     static const DWORD exp_caps = WICBitmapDecoderCapabilityCanDecodeAllImages |
457                                   WICBitmapDecoderCapabilityCanDecodeSomeImages |
458                                   WICBitmapDecoderCapabilityCanEnumerateMetadata;
459     static const DWORD exp_caps_xp = WICBitmapDecoderCapabilityCanDecodeAllImages |
460                                      WICBitmapDecoderCapabilityCanDecodeSomeImages;
461     DWORD capability;
462     LARGE_INTEGER pos;
463     ULARGE_INTEGER cur_pos;
464     UINT frame_count;
465 
466     stream = create_stream(&tiff_1bpp_data, sizeof(tiff_1bpp_data));
467     if (!stream) return;
468 
469     hr = IWICImagingFactory_CreateDecoder(factory, &GUID_ContainerFormatTiff, NULL, &decoder);
470     ok(hr == S_OK, "CreateDecoder error %#x\n", hr);
471     if (FAILED(hr)) return;
472 
473     frame_count = 0xdeadbeef;
474     hr = IWICBitmapDecoder_GetFrameCount(decoder, &frame_count);
475     ok(hr == S_OK || broken(hr == E_POINTER) /* XP */, "GetFrameCount error %#x\n", hr);
476     ok(frame_count == 0, "expected 0, got %u\n", frame_count);
477 
478     hr = IWICBitmapDecoder_GetFrame(decoder, 0, &frame);
479     ok(hr == WINCODEC_ERR_FRAMEMISSING || broken(hr == E_POINTER) /* XP */, "expected WINCODEC_ERR_FRAMEMISSING, got %#x\n", hr);
480 
481     pos.QuadPart = 4;
482     hr = IStream_Seek(stream, pos, SEEK_SET, NULL);
483     ok(hr == S_OK, "IStream_Seek error %#x\n", hr);
484 
485     capability = 0xdeadbeef;
486     hr = IWICBitmapDecoder_QueryCapability(decoder, stream, &capability);
487     ok(hr == S_OK, "QueryCapability error %#x\n", hr);
488     ok(capability == exp_caps || capability == exp_caps_xp,
489        "expected %#x, got %#x\n", exp_caps, capability);
490 
491     frame_count = 0xdeadbeef;
492     hr = IWICBitmapDecoder_GetFrameCount(decoder, &frame_count);
493     ok(hr == S_OK, "GetFrameCount error %#x\n", hr);
494     ok(frame_count == 1, "expected 1, got %u\n", frame_count);
495 
496     hr = IWICBitmapDecoder_GetFrame(decoder, 0, &frame);
497     ok(hr == S_OK, "GetFrame error %#x\n", hr);
498     IWICBitmapFrameDecode_Release(frame);
499 
500     pos.QuadPart = 0;
501     hr = IStream_Seek(stream, pos, SEEK_CUR, &cur_pos);
502     ok(hr == S_OK, "IStream_Seek error %#x\n", hr);
503     ok(cur_pos.QuadPart > 4 && cur_pos.QuadPart < sizeof(tiff_1bpp_data),
504        "current stream pos is at %x/%x\n", cur_pos.u.LowPart, cur_pos.u.HighPart);
505 
506     hr = IWICBitmapDecoder_QueryCapability(decoder, stream, &capability);
507     ok(hr == WINCODEC_ERR_WRONGSTATE, "expected WINCODEC_ERR_WRONGSTATE, got %#x\n", hr);
508 
509     hr = IWICBitmapDecoder_Initialize(decoder, stream, WICDecodeMetadataCacheOnDemand);
510     ok(hr == WINCODEC_ERR_WRONGSTATE, "expected WINCODEC_ERR_WRONGSTATE, got %#x\n", hr);
511 
512     IWICBitmapDecoder_Release(decoder);
513 
514     hr = IWICImagingFactory_CreateDecoderFromStream(factory, stream, NULL, 0, &decoder);
515 todo_wine
516     ok(hr == WINCODEC_ERR_COMPONENTNOTFOUND, "expected WINCODEC_ERR_COMPONENTNOTFOUND, got %#x\n", hr);
517 
518     if (SUCCEEDED(hr))
519         IWICBitmapDecoder_Release(decoder);
520 
521     pos.QuadPart = 0;
522     hr = IStream_Seek(stream, pos, SEEK_SET, NULL);
523     ok(hr == S_OK, "IStream_Seek error %#x\n", hr);
524 
525     hr = IWICImagingFactory_CreateDecoderFromStream(factory, stream, NULL, 0, &decoder);
526     ok(hr == S_OK, "CreateDecoderFromStream error %#x\n", hr);
527 
528     frame_count = 0xdeadbeef;
529     hr = IWICBitmapDecoder_GetFrameCount(decoder, &frame_count);
530     ok(hr == S_OK, "GetFrameCount error %#x\n", hr);
531     ok(frame_count == 1, "expected 1, got %u\n", frame_count);
532 
533     hr = IWICBitmapDecoder_GetFrame(decoder, 0, &frame);
534     ok(hr == S_OK, "GetFrame error %#x\n", hr);
535     IWICBitmapFrameDecode_Release(frame);
536 
537     hr = IWICBitmapDecoder_Initialize(decoder, stream, WICDecodeMetadataCacheOnDemand);
538     ok(hr == WINCODEC_ERR_WRONGSTATE, "expected WINCODEC_ERR_WRONGSTATE, got %#x\n", hr);
539 
540     hr = IWICBitmapDecoder_QueryCapability(decoder, stream, &capability);
541     ok(hr == WINCODEC_ERR_WRONGSTATE, "expected WINCODEC_ERR_WRONGSTATE, got %#x\n", hr);
542 
543     IWICBitmapDecoder_Release(decoder);
544     IStream_Release(stream);
545 }
546 
547 static void test_tiff_8bpp_alpha(void)
548 {
549     HRESULT hr;
550     IWICBitmapDecoder *decoder;
551     IWICBitmapFrameDecode *frame;
552     UINT frame_count, width, height, i;
553     double dpi_x, dpi_y;
554     IWICPalette *palette;
555     GUID format;
556     WICRect rc;
557     BYTE data[16];
558     static const BYTE expected_data[16] = { 0x11,0x11,0x11,0x22,0x33,0x33,0x33,0x44,
559                                             0x55,0x55,0x55,0x66,0x77,0x77,0x77,0x88 };
560 
561     hr = create_decoder(&tiff_8bpp_alpha, sizeof(tiff_8bpp_alpha), &decoder);
562     ok(hr == S_OK, "Failed to load TIFF image data %#x\n", hr);
563     if (hr != S_OK) return;
564 
565     hr = IWICBitmapDecoder_GetFrameCount(decoder, &frame_count);
566     ok(hr == S_OK, "GetFrameCount error %#x\n", hr);
567     ok(frame_count == 1, "expected 1, got %u\n", frame_count);
568 
569     EXPECT_REF(decoder, 1);
570     hr = IWICBitmapDecoder_GetFrame(decoder, 0, &frame);
571     ok(hr == S_OK, "GetFrame error %#x\n", hr);
572     EXPECT_REF(decoder, 2);
573     IWICBitmapDecoder_Release(decoder);
574 
575     hr = IWICBitmapFrameDecode_GetSize(frame, &width, &height);
576     ok(hr == S_OK, "GetSize error %#x\n", hr);
577     ok(width == 2, "expected 2, got %u\n", width);
578     ok(height == 2, "expected 2, got %u\n", height);
579 
580     hr = IWICBitmapFrameDecode_GetResolution(frame, &dpi_x, &dpi_y);
581     ok(hr == S_OK, "GetResolution error %#x\n", hr);
582     ok(dpi_x == 96.0, "expected 96.0, got %f\n", dpi_x);
583     ok(dpi_y == 96.0, "expected 96.0, got %f\n", dpi_y);
584 
585     hr = IWICBitmapFrameDecode_GetPixelFormat(frame, &format);
586     ok(hr == S_OK, "GetPixelFormat error %#x\n", hr);
587     ok(IsEqualGUID(&format, &GUID_WICPixelFormat32bppPBGRA),
588        "got wrong format %s\n", wine_dbgstr_guid(&format));
589 
590     hr = IWICImagingFactory_CreatePalette(factory, &palette);
591     ok(hr == S_OK, "CreatePalette error %#x\n", hr);
592     hr = IWICBitmapFrameDecode_CopyPalette(frame, palette);
593     ok(hr == WINCODEC_ERR_PALETTEUNAVAILABLE,
594        "expected WINCODEC_ERR_PALETTEUNAVAILABLE, got %#x\n", hr);
595     IWICPalette_Release(palette);
596 
597     rc.X = 0;
598     rc.Y = 0;
599     rc.Width = 2;
600     rc.Height = 2;
601     hr = IWICBitmapFrameDecode_CopyPixels(frame, &rc, 8, sizeof(data), data);
602     ok(hr == S_OK, "CopyPixels error %#x\n", hr);
603 
604     for (i = 0; i < sizeof(data); i++)
605         ok(data[i] == expected_data[i], "%u: expected %02x, got %02x\n", i, expected_data[i], data[i]);
606 
607     IWICBitmapFrameDecode_Release(frame);
608 }
609 
610 static void generate_tiff_palette(void *buf, unsigned count)
611 {
612     unsigned short *r, *g, *b;
613     unsigned i;
614 
615     r = buf;
616     g = r + count;
617     b = g + count;
618 
619     r[0] = 0x11 * 257;
620     g[0] = 0x22 * 257;
621     b[0] = 0x33 * 257;
622     r[1] = 0x44 * 257;
623     g[1] = 0x55 * 257;
624     b[1] = 0x66 * 257;
625     r[2] = 0x77 * 257;
626     g[2] = 0x88 * 257;
627     b[2] = 0x99 * 257;
628     r[3] = 0xa1 * 257;
629     g[3] = 0xb5 * 257;
630     b[3] = 0xff * 257;
631 
632     for (i = 4; i < count; i++)
633     {
634         r[i] = i * 257;
635         g[i] = (i | 0x40) * 257;
636         b[i] = (i | 0x80) * 257;
637     }
638 }
639 
640 static void test_tiff_8bpp_palette(void)
641 {
642     char buf[sizeof(tiff_8bpp_data)];
643     HRESULT hr;
644     IWICBitmapDecoder *decoder;
645     IWICBitmapFrameDecode *frame;
646     IWICPalette *palette;
647     GUID format;
648     UINT count, ret;
649     WICColor color[256];
650 
651     memcpy(buf, &tiff_8bpp_data, sizeof(tiff_8bpp_data));
652     generate_tiff_palette(buf + FIELD_OFFSET(struct tiff_8bpp_data, palette_data), 256);
653 
654     hr = create_decoder(buf, sizeof(buf), &decoder);
655     ok(hr == S_OK, "Failed to load TIFF image data %#x\n", hr);
656     if (hr != S_OK) return;
657 
658     hr = IWICBitmapDecoder_GetFrame(decoder, 0, &frame);
659     ok(hr == S_OK, "GetFrame error %#x\n", hr);
660 
661     hr = IWICBitmapFrameDecode_GetPixelFormat(frame, &format);
662     ok(hr == S_OK, "GetPixelFormat error %#x\n", hr);
663     ok(IsEqualGUID(&format, &GUID_WICPixelFormat8bppIndexed),
664        "expected GUID_WICPixelFormat8bppIndexed, got %s\n", wine_dbgstr_guid(&format));
665 
666     hr = IWICImagingFactory_CreatePalette(factory, &palette);
667     ok(hr == S_OK, "CreatePalette error %#x\n", hr);
668     hr = IWICBitmapFrameDecode_CopyPalette(frame, palette);
669     ok(hr == S_OK, "CopyPalette error %#x\n", hr);
670 
671     hr = IWICPalette_GetColorCount(palette, &count);
672     ok(hr == S_OK, "GetColorCount error %#x\n", hr);
673     ok(count == 256, "expected 256, got %u\n", count);
674 
675     hr = IWICPalette_GetColors(palette, 256, color, &ret);
676     ok(hr == S_OK, "GetColors error %#x\n", hr);
677     ok(ret == count, "expected %u, got %u\n", count, ret);
678     ok(color[0] == 0xff112233, "got %#x\n", color[0]);
679     ok(color[1] == 0xff445566, "got %#x\n", color[1]);
680     ok(color[2] == 0xff778899, "got %#x\n", color[2]);
681     ok(color[3] == 0xffa1b5ff, "got %#x\n", color[3]);
682 
683     IWICPalette_Release(palette);
684     IWICBitmapFrameDecode_Release(frame);
685     IWICBitmapDecoder_Release(decoder);
686 }
687 
688 static void test_tiff_resolution(void)
689 {
690     HRESULT hr;
691     IWICBitmapDecoder *decoder;
692     IWICBitmapFrameDecode *frame;
693     double dpi_x, dpi_y;
694     int i;
695 
696     for (i = 0; i < ARRAY_SIZE(tiff_resolution_test_data); i++)
697     {
698         const struct tiff_resolution_test_data *test_data = &tiff_resolution_test_data[i];
699         tiff_resolution_image_data.resx = test_data->resx;
700         tiff_resolution_image_data.resy = test_data->resy;
701         tiff_resolution_image_data.entry[12].value = test_data->resolution_unit;
702 
703         hr = create_decoder(&tiff_resolution_image_data, sizeof(tiff_resolution_image_data), &decoder);
704         ok(hr == S_OK, "Failed to load TIFF image data %#x\n", hr);
705         if (hr != S_OK) return;
706 
707         hr = IWICBitmapDecoder_GetFrame(decoder, 0, &frame);
708         ok(hr == S_OK, "%d: GetFrame error %#x\n", i, hr);
709 
710         hr = IWICBitmapFrameDecode_GetResolution(frame, &dpi_x, &dpi_y);
711         ok(hr == S_OK, "%d: GetResolution error %#x\n", i, hr);
712 
713         if (test_data->broken_dpi_x != 0)
714         {
715             ok(fabs(dpi_x - test_data->expected_dpi_x) < 0.01 || broken(fabs(dpi_x - test_data->broken_dpi_x) < 0.01),
716                 "%d: x: expected %f or %f, got %f\n", i, test_data->expected_dpi_x, test_data->broken_dpi_x, dpi_x);
717         }
718         else
719         {
720             ok(fabs(dpi_x - test_data->expected_dpi_x) < 0.01,
721                 "%d: x: expected %f, got %f\n", i, test_data->expected_dpi_x, dpi_x);
722         }
723 
724         if (test_data->broken_dpi_y != 0)
725         {
726             ok(fabs(dpi_y - test_data->expected_dpi_y) < 0.01 || broken(fabs(dpi_y - test_data->broken_dpi_y) < 0.01),
727                 "%d: y: expected %f or %f, got %f\n", i, test_data->expected_dpi_y, test_data->broken_dpi_y, dpi_y);
728         }
729         else
730         {
731             ok(fabs(dpi_y - test_data->expected_dpi_y) < 0.01,
732                 "%d: y: expected %f, got %f\n", i, test_data->expected_dpi_y, dpi_y);
733         }
734 
735         IWICBitmapFrameDecode_Release(frame);
736         IWICBitmapDecoder_Release(decoder);
737     }
738 }
739 
740 static void test_tiff_24bpp(void)
741 {
742     HRESULT hr;
743     IWICBitmapDecoder *decoder;
744     IWICBitmapFrameDecode *frame;
745     UINT count, width, height, i, stride;
746     double dpi_x, dpi_y;
747     GUID format;
748     WICRect rc;
749     BYTE data[3];
750     static const BYTE expected_data[] = { 0x33,0x22,0x11 };
751 
752     hr = create_decoder(&tiff_24bpp_data, sizeof(tiff_24bpp_data), &decoder);
753     ok(hr == S_OK, "Failed to load TIFF image data %#x\n", hr);
754     if (hr != S_OK) return;
755     ok(decoder != NULL, "Failed to load TIFF image data\n");
756 
757     hr = IWICBitmapDecoder_GetFrameCount(decoder, &count);
758     ok(hr == S_OK, "GetFrameCount error %#x\n", hr);
759     ok(count == 1, "got %u\n", count);
760 
761     hr = IWICBitmapDecoder_GetFrame(decoder, 0, &frame);
762     ok(hr == S_OK, "GetFrame error %#x\n", hr);
763 
764     hr = IWICBitmapFrameDecode_GetSize(frame, &width, &height);
765     ok(hr == S_OK, "GetSize error %#x\n", hr);
766     ok(width == 1, "got %u\n", width);
767     ok(height == 1, "got %u\n", height);
768 
769     hr = IWICBitmapFrameDecode_GetResolution(frame, &dpi_x, &dpi_y);
770     ok(hr == S_OK, "GetResolution error %#x\n", hr);
771     ok(dpi_x == 300.0, "got %f\n", dpi_x);
772     ok(dpi_y == 300.0, "got %f\n", dpi_y);
773 
774     hr = IWICBitmapFrameDecode_GetPixelFormat(frame, &format);
775     ok(hr == S_OK, "GetPixelFormat error %#x\n", hr);
776     ok(IsEqualGUID(&format, &GUID_WICPixelFormat24bppBGR),
777        "got wrong format %s\n", wine_dbgstr_guid(&format));
778 
779     for (stride = 0; stride <= 32; stride++)
780     {
781         memset(data, 0, sizeof(data));
782         rc.X = 0;
783         rc.Y = 0;
784         rc.Width = 1;
785         rc.Height = 1;
786         hr = IWICBitmapFrameDecode_CopyPixels(frame, &rc, stride, sizeof(data), data);
787         if (stride < 3)
788             ok(hr == E_INVALIDARG, "CopyPixels(%u) should fail: %#x\n", stride, hr);
789         else
790         {
791             ok(hr == S_OK, "CopyPixels(%u) error %#x\n", stride, hr);
792 
793             for (i = 0; i < sizeof(data); i++)
794                 ok(data[i] == expected_data[i], "%u: expected %02x, got %02x\n", i, expected_data[i], data[i]);
795         }
796     }
797 
798     IWICBitmapFrameDecode_Release(frame);
799     IWICBitmapDecoder_Release(decoder);
800 }
801 
802 #include "pshpack2.h"
803 static const struct tiff_1x1_data
804 {
805     USHORT byte_order;
806     USHORT version;
807     ULONG  dir_offset;
808     USHORT number_of_entries;
809     struct IFD_entry entry[12];
810     ULONG next_IFD;
811     struct IFD_rational res;
812     short palette_data[3][256];
813     short bps_data[4];
814     BYTE pixel_data[32];
815 } tiff_1x1_data =
816 {
817 #ifdef WORDS_BIGENDIAN
818     'M' | 'M' << 8,
819 #else
820     'I' | 'I' << 8,
821 #endif
822     42,
823     FIELD_OFFSET(struct tiff_1x1_data, number_of_entries),
824     12,
825     {
826         { 0xff, IFD_SHORT, 1, 0 }, /* SUBFILETYPE */
827         { 0x100, IFD_LONG, 1, 1 }, /* IMAGEWIDTH */
828         { 0x101, IFD_LONG, 1, 1 }, /* IMAGELENGTH */
829         { 0x102, IFD_SHORT, 3, FIELD_OFFSET(struct tiff_1x1_data, bps_data) }, /* BITSPERSAMPLE */
830         { 0x103, IFD_SHORT, 1, 1 }, /* COMPRESSION: XP doesn't accept IFD_LONG here */
831         { 0x106, IFD_SHORT, 1, 2 }, /* PHOTOMETRIC */
832         { 0x111, IFD_LONG, 1, FIELD_OFFSET(struct tiff_1x1_data, pixel_data) }, /* STRIPOFFSETS */
833         { 0x115, IFD_SHORT, 1, 3 }, /* SAMPLESPERPIXEL */
834         { 0x11a, IFD_RATIONAL, 1, FIELD_OFFSET(struct tiff_1x1_data, res) },
835         { 0x11b, IFD_RATIONAL, 1, FIELD_OFFSET(struct tiff_1x1_data, res) },
836         { 0x128, IFD_SHORT, 1, 2 }, /* RESOLUTIONUNIT */
837         { 0x140, IFD_SHORT, 256*3, FIELD_OFFSET(struct tiff_1x1_data, palette_data) } /* COLORMAP */
838     },
839     0,
840     { 96, 1 },
841     { { 0 } },
842     { 8,8,8,0 },
843     { 1,0,2,3,4,5,6,7,8,9,0,1,2,3,4,5 }
844 };
845 #include "poppack.h"
846 
847 static UINT width_bytes(UINT width, UINT bpp)
848 {
849     return (width * bpp + 7) / 8;
850 }
851 
852 static void test_color_formats(void)
853 {
854     struct bitmap_data
855     {
856         UINT bpp;
857         UINT width;
858         UINT height;
859         const WICPixelFormatGUID *format;
860         const BYTE *bits;
861     };
862     static const BYTE bits_1bpsBGR[] = { 0,255,0,255,0,255,255,255,0,0,0,255,255,0,0,0,255,255,255,255,255,0,0,0,0,255,0,255,0,255 };
863     static const struct bitmap_data data_1bpsBGR =
864     {
865         24, 10, 2, &GUID_WICPixelFormat24bppBGR, bits_1bpsBGR
866     };
867     static const BYTE bits_4bpsBGR[] = { 204,85,85,136,187,51,0,85,85,85,0,68,0,102,0,136,0,119,0,153,0 };
868     static const struct bitmap_data data_4bpsBGR =
869     {
870         24, 5, 2, &GUID_WICPixelFormat24bppBGR, bits_4bpsBGR
871     };
872     static const BYTE bits_8bpsBGR[] = { 2,0,1,5,4,3,8,7,6 };
873     static const struct bitmap_data data_8bpsBGR =
874     {
875         24, 3, 1, &GUID_WICPixelFormat24bppBGR, bits_8bpsBGR
876     };
877     static const BYTE bits_48bppRGB[] = { 1,0,2,3,4,5,6,7,8,9,0,1 };
878     static const struct bitmap_data data_48bppRGB =
879     {
880         48, 2, 1, &GUID_WICPixelFormat48bppRGB, bits_48bppRGB
881     };
882     static const BYTE bits_1bpsBGRA[] = { 0,255,0,255,0,255,0,255,0,255,255,0,255,0,0,255,255,0,255,255,0,0,255,0,0,255,0,255,0,255,0,255,0,0,0,0,0,255,0,0 };
883     static const struct bitmap_data data_1bpsBGRA =
884     {
885         32, 5, 2, &GUID_WICPixelFormat32bppBGRA, bits_1bpsBGRA
886     };
887     static const BYTE bits_4bpsBGRA[] = { 204,85,85,51,85,136,187,85,0,68,0,85,0,102,0,119,0,136,0,153,0,0,0,17,0,34,0,51 };
888     static const struct bitmap_data data_4bpsBGRA =
889     {
890         32, 5, 2, &GUID_WICPixelFormat32bppBGRA, bits_4bpsBGRA
891     };
892     static const BYTE bits_8bpsBGRA[] = { 2,0,1,3,6,5,4,7,0,9,8,1,4,3,2,5 };
893     static const struct bitmap_data data_8bpsBGRA =
894     {
895         32, 4, 1, &GUID_WICPixelFormat32bppBGRA, bits_8bpsBGRA
896     };
897     static const BYTE bits_64bppRGBA[] = { 1,0,2,3,4,5,6,7,8,9,0,1,2,3,4,5 };
898     static const struct bitmap_data data_64bppRGBA =
899     {
900         64, 2, 1, &GUID_WICPixelFormat64bppRGBA, bits_64bppRGBA
901     };
902     static const BYTE bits_BlackWhite[] = { 85,195,184,85 };
903     static const struct bitmap_data data_BlackWhite =
904     {
905         1, 30, 1, &GUID_WICPixelFormatBlackWhite, bits_BlackWhite
906     };
907     static const BYTE bits_BlackWhite_xp[] = { 85,195,184,84 };
908     static const struct bitmap_data data_BlackWhite_xp =
909     {
910         1, 30, 1, &GUID_WICPixelFormatBlackWhite, bits_BlackWhite_xp
911     };
912     static const BYTE bits_4bppGray[] = { 85,195,184,85 };
913     static const struct bitmap_data data_4bppGray =
914     {
915         4, 7, 1, &GUID_WICPixelFormat4bppGray, bits_4bppGray
916     };
917     static const BYTE bits_4bppGray_xp[] = { 85,195,184,80 };
918     static const struct bitmap_data data_4bppGray_xp =
919     {
920         4, 7, 1, &GUID_WICPixelFormat4bppGray, bits_4bppGray_xp
921     };
922     static const BYTE bits_8bppGray[] = { 1,0,2,3,4,5,6,7,8,9 };
923     static const struct bitmap_data data_8bppGray =
924     {
925         8, 10, 1, &GUID_WICPixelFormat8bppGray, bits_8bppGray
926     };
927     static const BYTE bits_16bppGray[] = { 1,0,2,3,4,5 };
928     static const struct bitmap_data data_16bppGray =
929     {
930         16, 3, 1, &GUID_WICPixelFormat16bppGray, bits_16bppGray
931     };
932     static const BYTE bits_32bppGrayFloat[] = { 1,0,2,3,4,5,6,7,8,9,0,1 };
933     static const struct bitmap_data data_32bppGrayFloat =
934     {
935         32, 3, 1, &GUID_WICPixelFormat32bppGrayFloat, bits_32bppGrayFloat
936     };
937 #if 0 /* FIXME */
938     static const BYTE bits_96bpp3Channels[] = { 0 };
939     static const struct bitmap_data data_96bpp3Channels =
940     {
941         64, 1, 1, &GUID_WICPixelFormat96bpp3Channels, bits_96bpp3Channels
942     };
943 #endif
944     static const BYTE bits_128bppRGBAFloat[] = { 1,0,2,3,4,5,6,7,8,9,0,1,2,3,4,5 };
945     static const struct bitmap_data data_128bppRGBAFloat =
946     {
947         128, 1, 1, &GUID_WICPixelFormat128bppRGBAFloat, bits_128bppRGBAFloat
948     };
949     static const BYTE bits_1bppIndexed[] = { 85,195,184,85 };
950     static const struct bitmap_data data_1bppIndexed =
951     {
952         1, 32, 1, &GUID_WICPixelFormat1bppIndexed, bits_1bppIndexed
953     };
954     static const BYTE bits_4bppIndexed[] = { 85,195,184,85 };
955     static const struct bitmap_data data_4bppIndexed =
956     {
957         4, 7, 1, &GUID_WICPixelFormat4bppIndexed, bits_4bppIndexed
958     };
959     static const BYTE bits_4bppIndexed_xp[] = { 85,195,184,80 };
960     static const struct bitmap_data data_4bppIndexed_xp =
961     {
962         4, 7, 1, &GUID_WICPixelFormat4bppIndexed, bits_4bppIndexed_xp
963     };
964     static const BYTE bits_8bppIndexed[] = { 1,0,2,3,4,5,6,7,8,9 };
965     static const struct bitmap_data data_8bppIndexed =
966     {
967         8, 3, 1, &GUID_WICPixelFormat8bppIndexed, bits_8bppIndexed
968     };
969     static const BYTE bits_32bppCMYK[] = { 1,0,2,3,4,5,6,7,8,9,0,1 };
970     static const struct bitmap_data data_32bppCMYK =
971     {
972         32, 3, 1, &GUID_WICPixelFormat32bppCMYK, bits_32bppCMYK
973     };
974     static const BYTE bits_64bppCMYK[] = { 1,0,2,3,4,5,6,7,8,9,0,1,2,3,4,5 };
975     static const struct bitmap_data data_64bppCMYK =
976     {
977         64, 2, 1, &GUID_WICPixelFormat64bppCMYK, bits_64bppCMYK
978     };
979     static const struct
980     {
981         int photometric; /* PhotometricInterpretation */
982         int samples; /* SamplesPerPixel */
983         int bps; /* BitsPerSample */
984         const struct bitmap_data *data;
985         const struct bitmap_data *alt_data;
986     } td[] =
987     {
988         /* 2 - RGB */
989         { 2, 3, 1, &data_1bpsBGR },
990         { 2, 3, 4, &data_4bpsBGR },
991         { 2, 3, 8, &data_8bpsBGR },
992         { 2, 3, 16, &data_48bppRGB },
993         { 2, 3, 24, NULL },
994 #if 0 /* FIXME */
995         { 2, 3, 32, &data_96bpp3Channels },
996 #endif
997         { 2, 4, 1, &data_1bpsBGRA },
998         { 2, 4, 4, &data_4bpsBGRA },
999         { 2, 4, 8, &data_8bpsBGRA },
1000         { 2, 4, 16, &data_64bppRGBA },
1001         { 2, 4, 24, NULL },
1002         { 2, 4, 32, &data_128bppRGBAFloat },
1003         /* 1 - BlackIsZero (Bilevel) */
1004         { 1, 1, 1, &data_BlackWhite, &data_BlackWhite_xp },
1005         { 1, 1, 4, &data_4bppGray, &data_4bppGray_xp },
1006         { 1, 1, 8, &data_8bppGray },
1007         { 1, 1, 16, &data_16bppGray },
1008         { 1, 1, 24, NULL },
1009         { 1, 1, 32, &data_32bppGrayFloat },
1010         /* 3 - Palette Color */
1011         { 3, 1, 1, &data_1bppIndexed },
1012         { 3, 1, 4, &data_4bppIndexed, &data_4bppIndexed_xp },
1013         { 3, 1, 8, &data_8bppIndexed },
1014 #if 0 /* FIXME: for some reason libtiff replaces photometric 3 by 1 for bps > 8 */
1015         { 3, 1, 16, &data_8bppIndexed },
1016         { 3, 1, 24, &data_8bppIndexed },
1017         { 3, 1, 32, &data_8bppIndexed },
1018 #endif
1019         /* 5 - Separated */
1020         { 5, 4, 1, NULL },
1021         { 5, 4, 4, NULL },
1022         { 5, 4, 8, &data_32bppCMYK },
1023         { 5, 4, 16, &data_64bppCMYK },
1024         { 5, 4, 24, NULL },
1025         { 5, 4, 32, NULL },
1026     };
1027     BYTE buf[sizeof(tiff_1x1_data)];
1028     BYTE pixels[256];
1029     HRESULT hr;
1030     IWICBitmapDecoder *decoder;
1031     IWICBitmapFrameDecode *frame;
1032     GUID format;
1033     UINT count, i, bpp, channels, ret;
1034     BOOL trasparency;
1035     struct IFD_entry *tag, *tag_photo = NULL, *tag_bps = NULL, *tag_samples = NULL, *tag_colormap = NULL;
1036     struct IFD_entry *tag_width = NULL, *tag_height = NULL;
1037     short *bps;
1038 
1039     memcpy(buf, &tiff_1x1_data, sizeof(tiff_1x1_data));
1040     generate_tiff_palette(buf + FIELD_OFFSET(struct tiff_1x1_data, palette_data), 256);
1041 
1042     count = *(short *)(buf + tiff_1x1_data.dir_offset);
1043     tag = (struct IFD_entry *)(buf + tiff_1x1_data.dir_offset + sizeof(short));
1044 
1045     /* verify the TIFF structure */
1046     for (i = 0; i < count; i++)
1047     {
1048         if (tag[i].id == 0x100) /* ImageWidth */
1049             tag_width = &tag[i];
1050         else if (tag[i].id == 0x101) /* ImageLength */
1051             tag_height = &tag[i];
1052         else if (tag[i].id == 0x102) /* BitsPerSample */
1053             tag_bps = &tag[i];
1054         else if (tag[i].id == 0x106) /* PhotometricInterpretation */
1055             tag_photo = &tag[i];
1056         else if (tag[i].id == 0x115) /* SamplesPerPixel */
1057             tag_samples = &tag[i];
1058         else if (tag[i].id == 0x140) /* ColorMap */
1059             tag_colormap = &tag[i];
1060     }
1061 
1062     ok(tag_bps && tag_photo && tag_samples && tag_colormap, "tag 0x102,0x106,0x115 or 0x140 is missing\n");
1063     if (!tag_bps || !tag_photo || !tag_samples || !tag_colormap) return;
1064 
1065     ok(tag_bps->type == IFD_SHORT, "tag 0x102 should have type IFD_SHORT\n");
1066     bps = (short *)(buf + tag_bps->value);
1067     ok(bps[0] == 8 && bps[1] == 8 && bps[2] == 8 && bps[3] == 0,
1068        "expected bps 8,8,8,0 got %d,%d,%d,%d\n", bps[0], bps[1], bps[2], bps[3]);
1069 
1070     for (i = 0; i < sizeof(td)/sizeof(td[0]); i++)
1071     {
1072         if (td[i].data)
1073         {
1074             bpp = td[i].samples * td[i].bps;
1075             if (winetest_debug > 1)
1076                 trace("samples %u, bps %u, bpp %u, width %u => width_bytes %u\n", td[i].samples, td[i].bps, bpp,
1077                       td[i].data->width, width_bytes(td[i].data->width, bpp));
1078             tag_width->value = td[i].data->width;
1079             tag_height->value = td[i].data->height;
1080         }
1081         else
1082         {
1083             tag_width->value = 1;
1084             tag_height->value = 1;
1085         }
1086 
1087         tag_colormap->count = (1 << td[i].bps) * 3;
1088 
1089         if (td[i].bps < 8)
1090         {
1091             buf[FIELD_OFFSET(struct tiff_1x1_data, pixel_data)] = 0x55;
1092             buf[FIELD_OFFSET(struct tiff_1x1_data, pixel_data) + 1] = 0xc3;
1093             buf[FIELD_OFFSET(struct tiff_1x1_data, pixel_data) + 2] = 0xb8;
1094             buf[FIELD_OFFSET(struct tiff_1x1_data, pixel_data) + 3] = 0x55;
1095         }
1096         else
1097         {
1098             buf[FIELD_OFFSET(struct tiff_1x1_data, pixel_data)] = 1;
1099             buf[FIELD_OFFSET(struct tiff_1x1_data, pixel_data) + 1] = 0;
1100             buf[FIELD_OFFSET(struct tiff_1x1_data, pixel_data) + 2] = 2;
1101             buf[FIELD_OFFSET(struct tiff_1x1_data, pixel_data) + 3] = 3;
1102         }
1103 
1104         tag_photo->value = td[i].photometric;
1105         tag_bps->count = td[i].samples;
1106         tag_samples->value = td[i].samples;
1107 
1108         if (td[i].samples == 1)
1109             tag_bps->value = td[i].bps;
1110         else if (td[i].samples == 2)
1111             tag_bps->value = MAKELONG(td[i].bps, td[i].bps);
1112         else if (td[i].samples == 3)
1113         {
1114             tag_bps->value = (BYTE *)bps - buf;
1115             bps[0] = bps[1] = bps[2] = td[i].bps;
1116         }
1117         else if (td[i].samples == 4)
1118         {
1119             tag_bps->value = (BYTE *)bps - buf;
1120             bps[0] = bps[1] = bps[2] = bps[3] = td[i].bps;
1121         }
1122         else
1123         {
1124             ok(0, "%u: unsupported samples count %d\n", i, td[i].samples);
1125             continue;
1126         }
1127 
1128         hr = create_decoder(buf, sizeof(buf), &decoder);
1129         if (!td[i].data)
1130         {
1131             ok(hr == WINCODEC_ERR_UNSUPPORTEDPIXELFORMAT || hr == WINCODEC_ERR_COMPONENTNOTFOUND /* win8+ */ || WINCODEC_ERR_BADIMAGE /* XP */,
1132                "%u: (%d,%d,%d) wrong error %#x\n", i, td[i].photometric, td[i].samples, td[i].bps, hr);
1133             if (hr == S_OK)
1134             {
1135                 IWICBitmapDecoder_Release(decoder);
1136                 dump_tiff(buf);
1137             }
1138             continue;
1139         }
1140         else
1141             ok(hr == S_OK || broken(hr == WINCODEC_ERR_UNSUPPORTEDPIXELFORMAT || hr == WINCODEC_ERR_BADIMAGE) /* XP */,
1142                "%u: failed to load TIFF image data (%d,%d,%d) %#x\n",
1143                i, td[i].photometric, td[i].samples, td[i].bps, hr);
1144         if (hr != S_OK) continue;
1145 
1146         hr = IWICBitmapDecoder_GetFrame(decoder, 0, &frame);
1147         ok(hr == S_OK, "%u: GetFrame error %#x\n", i, hr);
1148 
1149         hr = IWICBitmapFrameDecode_GetPixelFormat(frame, &format);
1150         ok(hr == S_OK, "%u: GetPixelFormat error %#x\n", i, hr);
1151         ok(IsEqualGUID(&format, td[i].data->format),
1152            "%u (%d,%d,%d): expected %s, got %s\n",
1153             i, td[i].photometric, td[i].samples, td[i].bps,
1154             wine_dbgstr_guid(td[i].data->format), wine_dbgstr_guid(&format));
1155 
1156         trasparency = (td[i].photometric == 2 && td[i].samples == 4); /* for XP */
1157         hr = get_pixelformat_info(&format, &bpp, &channels, &trasparency);
1158         ok(hr == S_OK, "%u: get_pixelformat_bpp error %#x\n", i, hr);
1159         ok(bpp == td[i].data->bpp, "%u: expected %u, got %u\n", i, td[i].data->bpp, bpp);
1160         ok(channels == td[i].samples, "%u: expected %u, got %u\n", i, td[i].samples, channels);
1161         ok(trasparency == (td[i].photometric == 2 && td[i].samples == 4), "%u: got %u\n", i, trasparency);
1162 
1163         memset(pixels, 0, sizeof(pixels));
1164         hr = IWICBitmapFrameDecode_CopyPixels(frame, NULL, width_bytes(td[i].data->width, bpp), sizeof(pixels), pixels);
1165         ok(hr == S_OK, "%u: CopyPixels error %#x\n", i, hr);
1166         ret = memcmp(pixels, td[i].data->bits, width_bytes(td[i].data->width, bpp));
1167         if (ret && td[i].alt_data)
1168             ret = memcmp(pixels, td[i].alt_data->bits, width_bytes(td[i].data->width, bpp));
1169         ok(ret == 0, "%u: (%d,%d,%d) wrong pixel data\n", i, td[i].photometric, td[i].samples, td[i].bps);
1170         if (ret)
1171         {
1172             UINT j, n = width_bytes(td[i].data->width, bpp);
1173             for (j = 0; j < n; j++)
1174                 printf("%u%s", pixels[j], (j + 1) < n ? "," : "\n");
1175         }
1176 
1177         IWICBitmapFrameDecode_Release(frame);
1178         IWICBitmapDecoder_Release(decoder);
1179     }
1180 }
1181 
1182 START_TEST(tiffformat)
1183 {
1184     HRESULT hr;
1185 
1186     CoInitializeEx(NULL, COINIT_APARTMENTTHREADED);
1187 
1188     hr = CoCreateInstance(&CLSID_WICImagingFactory, NULL, CLSCTX_INPROC_SERVER,
1189                           &IID_IWICImagingFactory, (void **)&factory);
1190     ok(hr == S_OK, "CoCreateInstance error %#x\n", hr);
1191     if (FAILED(hr)) return;
1192 
1193     test_color_formats();
1194     test_tiff_1bpp_palette();
1195     test_tiff_8bpp_palette();
1196     test_QueryCapability();
1197     test_tiff_8bpp_alpha();
1198     test_tiff_resolution();
1199     test_tiff_24bpp();
1200 
1201     IWICImagingFactory_Release(factory);
1202     CoUninitialize();
1203 }
1204