1 /*
2  * PROJECT:         ReactOS api tests
3  * LICENSE:         GPL - See COPYING in the top level directory
4  * PURPOSE:         Test for MaskBlt
5  * PROGRAMMERS:     Timo Kreuzer
6  */
7 
8 #include "precomp.h"
9 
10 #include "init.h"
11 
Test_MaskBlt_1bpp()12 void Test_MaskBlt_1bpp()
13 {
14     HDC hdcDst, hdcSrc;
15     struct
16     {
17         BITMAPINFOHEADER bmiHeader;
18         ULONG aulColors[2];
19     } bmiData = {{sizeof(BITMAPINFOHEADER), 8, 1, 1, 1, BI_RGB, 0, 10, 10, 2,0}, {0, 0xFFFFFF}};
20     PBITMAPINFO pbmi = (PBITMAPINFO)&bmiData;
21     HBITMAP hbmDst, hbmSrc, hbmMsk;
22     PUCHAR pjBitsDst, pjBitsSrc, pjBitsMsk;
23     BOOL ret;
24 
25     /* Create a dest dc and bitmap */
26     hdcDst = CreateCompatibleDC(NULL);
27     hbmDst = CreateDIBSection(hdcDst, pbmi, DIB_RGB_COLORS, (PVOID*)&pjBitsDst, NULL, 0);
28     SelectObject(hdcDst, hbmDst);
29 
30     /* Create a source dc and bitmap */
31     hdcSrc = CreateCompatibleDC(NULL);
32     hbmSrc = CreateDIBSection(hdcSrc, pbmi, DIB_RGB_COLORS, (PVOID*)&pjBitsSrc, NULL, 0);
33     SelectObject(hdcSrc, hbmSrc);
34 
35     /* Create a 1 bpp mask bitmap */
36     hbmMsk = CreateDIBSection(hdcDst, pbmi, DIB_RGB_COLORS, (PVOID*)&pjBitsMsk, NULL, 0);
37 
38     /* Do the masking (SRCCOPY / NOOP) */
39     pjBitsDst[0] = 0xAA;
40     pjBitsSrc[0] = 0xCC;
41     pjBitsMsk[0] = 0xF0;
42     SetLastError(0xDEADBEEF);
43     ret = MaskBlt(hdcDst, 0, 0, 8, 1, hdcSrc, 0, 0, hbmMsk, 0, 0, MAKEROP4(SRCCOPY, 0xAA0000));
44     ok_err(0xDEADBEEF);
45     ok(ret == 1, "MaskBlt failed (%d)\n", ret);
46     ok(pjBitsDst[0] == 0xCA, "pjBitsDst[0] == 0x%x\n", pjBitsDst[0]);
47 
48     pjBitsDst[0] = 0x00;
49     pjBitsSrc[0] = 0xFF;
50     pjBitsMsk[0] = 0xF0;
51     SetLastError(0xDEADBEEF);
52     ret = MaskBlt(hdcDst, 0, 0, 8, 1, hdcSrc, 0, 0, hbmMsk, 0, 0, MAKEROP4(SRCCOPY, 0xAA0000));
53     ok_err(0xDEADBEEF);
54     ok(ret == 1, "MaskBlt failed (%d)\n", ret);
55     ok(pjBitsDst[0] == 0xF0, "pjBitsDst[0] == 0x%x\n", pjBitsDst[0]);
56 
57     /* Do the masking (NOTSRCERASE / SRCINVERT) */
58     pjBitsDst[0] = 0xF0; // 11110000
59     pjBitsSrc[0] = 0xCC; // 11001100
60     pjBitsMsk[0] = 0xAA; // 10101010
61 
62     SetLastError(0xDEADBEEF);
63     ret = MaskBlt(hdcDst, 0, 0, 8, 1, hdcSrc, 0, 0, hbmMsk, 0, 0, MAKEROP4(NOTSRCERASE, SRCINVERT)); // 22
64     ok_err(0xDEADBEEF);
65     ok(ret == 1, "MaskBlt failed (%d)\n", ret);
66     ok(pjBitsDst[0] == 0x16, "pjBitsDst[0] == 0x%x\n", pjBitsDst[0]);
67 
68     /* Do the masking (MERGEPAINT / DSxn) */
69     pjBitsDst[0] = 0xF0;
70     pjBitsSrc[0] = 0xCC;
71     pjBitsMsk[0] = 0xAA;
72     SetLastError(0xDEADBEEF);
73     ret = MaskBlt(hdcDst, 0, 0, 8, 1, hdcSrc, 0, 0, hbmMsk, 0, 0, MAKEROP4(MERGEPAINT, 0x990000));
74     ok_err(0xDEADBEEF);
75     ok(ret == 1, "MaskBlt failed (%d)\n", ret);
76     ok(pjBitsDst[0] == 0xE3, "pjBitsDst[0] == 0x%x\n", pjBitsDst[0]);
77 
78     /* Try a ROP that needs a mask with a NULL mask bitmap handle */
79     SetLastError(0xDEADBEEF);
80     ret = MaskBlt(hdcDst, 0, 0, 8, 1, hdcSrc, 0, 0, NULL, 0, 0, MAKEROP4(SRCCOPY, 0xAA0000));
81     ok_err(0xDEADBEEF);
82     ok(ret == 1, "MaskBlt failed (%d)\n", ret);
83     ok(pjBitsDst[0] == 0xCC, "pjBitsDst[0] == 0x%x\n", pjBitsDst[0]);
84 
85     /* Try a ROP that needs a mask with an invalid mask bitmap handle */
86     SetLastError(0xDEADBEEF);
87     ret = MaskBlt(hdcDst, 0, 0, 8, 1, hdcSrc, 0, 0, (HBITMAP)0x123456, 0, 0, MAKEROP4(SRCCOPY, 0xAA0000));
88     ok_err(ERROR_INVALID_HANDLE);
89     ok(ret == 0, "MaskBlt should fail, but succeeded (%d)\n", ret);
90 
91     /* Try a ROP that needs a mask with an invalid mask bitmap */
92     ok(ghbmp24 != NULL, "ghbmp24 is NULL!\n");
93     SetLastError(0xDEADBEEF);
94     ret = MaskBlt(hdcDst, 0, 0, 8, 1, hdcSrc, 0, 0, ghbmp24, 0, 0, MAKEROP4(SRCCOPY, 0xAA0000));
95     ok_err(ERROR_INVALID_HANDLE);
96     ok(ret == 0, "MaskBlt should fail, but succeeded (%d)\n", ret);
97 
98     /* Try a ROP that needs no mask with an invalid mask bitmap */
99     SetLastError(0xDEADBEEF);
100     ret = MaskBlt(hdcDst, 0, 0, 8, 1, hdcSrc, 0, 0, (HBITMAP)0x123456, 0, 0, MAKEROP4(SRCCOPY, SRCCOPY));
101     ok_err(0xDEADBEEF);
102     ok(ret == 1, "MaskBlt failed (%d)\n", ret);
103 
104     /* Try (PATCOPY / NOOP) with a NULL source mask and bitmap */
105     SetLastError(0xDEADBEEF);
106     ret = MaskBlt(hdcDst, 0, 0, 8, 1, NULL, 0, 0, NULL, 0, 0, MAKEROP4(PATCOPY, 0xAA0000));
107     ok_err(0xDEADBEEF);
108     ok(ret == 0, "MaskBlt should fail, but succeeded (%d)\n", ret);
109 
110     /* Try with a mask that is smaller than the rect */
111     DeleteObject(hbmMsk);
112     pbmi->bmiHeader.biWidth = 4;
113     hbmMsk = CreateDIBSection(hdcDst, pbmi, DIB_RGB_COLORS, (PVOID*)&pjBitsMsk, NULL, 0);
114 
115     /* Do the masking (SRCCOPY / NOOP) */
116     pjBitsDst[0] = 0xAA; // 10101010
117     pjBitsSrc[0] = 0xCC; // 11001100
118     pjBitsMsk[0] = 0x33; // 00110011
119 
120     SetLastError(0xDEADBEEF);
121     ret = MaskBlt(hdcDst, 0, 0, 5, 1, hdcSrc, 0, 0, hbmMsk, 0, 0, MAKEROP4(SRCCOPY, 0xAA0000));
122     ok_err(ERROR_INVALID_PARAMETER);
123     ok(ret == 0, "MaskBlt should fail, but succeeded (%d)\n", ret);
124 
125     SetLastError(0xDEADBEEF);
126     ret = MaskBlt(hdcDst, 0, 0, 4, 1, hdcSrc, 0, 0, hbmMsk, 1, 0, MAKEROP4(SRCCOPY, 0xAA0000));
127     ok_err(ERROR_INVALID_PARAMETER);
128     ok(ret == 0, "MaskBlt should fail, but succeeded (%d)\n", ret);
129 
130     SetLastError(0xDEADBEEF);
131     ret = MaskBlt(hdcDst, 0, 0, 4, 1, hdcSrc, 0, 0, hbmMsk, 0, 1, MAKEROP4(SRCCOPY, 0xAA0000));
132     ok_err(ERROR_INVALID_PARAMETER);
133     ok(ret == 0, "MaskBlt should fail, but succeeded (%d)\n", ret);
134 
135     SetLastError(0xDEADBEEF);
136     ret = MaskBlt(hdcDst, 0, 0, 4, 1, hdcSrc, 0, 0, hbmMsk, 0, 0, MAKEROP4(SRCCOPY, 0xAA0000));
137     ok_err(0xDEADBEEF);
138     ok(ret == 1, "MaskBlt failed (%d)\n", ret);
139     ok(pjBitsDst[0] == 0x8A, "pjBitsDst[0] == 0x%x\n", pjBitsDst[0]);
140 }
141 
Test_MaskBlt_16bpp()142 void Test_MaskBlt_16bpp()
143 {
144     HDC hdcDst, hdcSrc;
145     BITMAPINFO bmi1 = {{sizeof(BITMAPINFOHEADER), 8, 1, 1, 1, BI_RGB, 0, 10, 10, 0,0}};
146     BITMAPINFO bmi32 = {{sizeof(BITMAPINFOHEADER), 8, 1, 1, 16, BI_RGB, 0, 10, 10, 0,0}};
147     HBITMAP hbmDst, hbmSrc, hbmMsk;
148     PUCHAR pjBitsMsk;
149     PUSHORT pusBitsDst, pusBitsSrc;
150     BOOL ret;
151 
152     /* Create a dest dc and bitmap */
153     hdcDst = CreateCompatibleDC(NULL);
154     hbmDst = CreateDIBSection(hdcDst, &bmi32, DIB_RGB_COLORS, (PVOID*)&pusBitsDst, NULL, 0);
155     SelectObject(hdcDst, hbmDst);
156 
157     /* Create a source dc and bitmap */
158     hdcSrc = CreateCompatibleDC(NULL);
159     hbmSrc = CreateDIBSection(hdcSrc, &bmi32, DIB_RGB_COLORS, (PVOID*)&pusBitsSrc, NULL, 0);
160     SelectObject(hdcSrc, hbmSrc);
161     ok(hdcSrc && hbmSrc, "\n");
162 
163     /* Create a 1 bpp mask bitmap */
164     hbmMsk = CreateDIBSection(hdcDst, &bmi1, DIB_RGB_COLORS, (PVOID*)&pjBitsMsk, NULL, 0);
165     ok(hbmMsk != 0, "CreateDIBSection failed\n");
166 
167     /* Do the masking */
168     pusBitsDst[0] = 0x1234;
169     pusBitsDst[1] = 0x5678;
170     pusBitsSrc[0] = 0x4321;
171     pusBitsSrc[1] = 0x8765;
172     pjBitsMsk[0] = 0x80;
173     SetLastError(0xDEADBEEF);
174     ret = MaskBlt(hdcDst, 0, 0, 8, 1, hdcSrc, 0, 0, hbmMsk, 0, 0, MAKEROP4(SRCCOPY, 0xAA0000));
175     ok_err(0xDEADBEEF);
176     ok(ret == 1, "MaskBlt failed (%d)\n", ret);
177     ok (pusBitsDst[0] == 0x4321, "pusBitsDst[0] == 0x%x\n", pusBitsDst[0]);
178     ok (pusBitsDst[1] == 0x5678, "pusBitsDst[0] == 0x%x\n", pusBitsDst[1]);
179 
180     pusBitsDst[0] = 0x1234;
181     pusBitsDst[1] = 0x5678;
182     SetLastError(0xDEADBEEF);
183     ret = MaskBlt(hdcDst, 0, 0, 8, 1, hdcSrc, 0, 0, hbmMsk, 0, 0, MAKEROP4(SRCPAINT, MERGEPAINT));
184     ok_err(0xDEADBEEF);
185     ok(ret == 1, "MaskBlt failed (%d)\n", ret);
186     ok (pusBitsDst[0] == 0x5335, "pusBitsDst[0] == 0x%x\n", pusBitsDst[0]);
187     ok (pusBitsDst[1] == 0x7efa, "pusBitsDst[0] == 0x%x\n", pusBitsDst[1]);
188 }
189 
Test_MaskBlt_32bpp()190 void Test_MaskBlt_32bpp()
191 {
192     HDC hdcDst, hdcSrc;
193     BITMAPINFO bmi1 = {{sizeof(BITMAPINFOHEADER), 8, 1, 1, 1, BI_RGB, 0, 10, 10, 0,0}};
194     BITMAPINFO bmi32 = {{sizeof(BITMAPINFOHEADER), 8, 1, 1, 32, BI_RGB, 0, 10, 10, 0,0}};
195     HBITMAP hbmDst, hbmSrc, hbmMsk;
196     PUCHAR pjBitsMsk;
197     PULONG pulBitsDst, pulBitsSrc;
198     BOOL ret;
199 
200     /* Create a dest dc and bitmap */
201     hdcDst = CreateCompatibleDC(NULL);
202     hbmDst = CreateDIBSection(hdcDst, &bmi32, DIB_RGB_COLORS, (PVOID*)&pulBitsDst, NULL, 0);
203     SelectObject(hdcDst, hbmDst);
204 
205     /* Create a source dc and bitmap */
206     hdcSrc = CreateCompatibleDC(NULL);
207     hbmSrc = CreateDIBSection(hdcSrc, &bmi32, DIB_RGB_COLORS, (PVOID*)&pulBitsSrc, NULL, 0);
208     SelectObject(hdcSrc, hbmSrc);
209     ok(hdcSrc && hbmSrc, "\n");
210 
211     /* Create a 1 bpp mask bitmap */
212     hbmMsk = CreateDIBSection(hdcDst, &bmi1, DIB_RGB_COLORS, (PVOID*)&pjBitsMsk, NULL, 0);
213     ok(hbmMsk != 0, "CreateDIBSection failed\n");
214 
215     /* Do the masking */
216     pulBitsDst[0] = 0x12345678;
217     pulBitsDst[1] = 0x9abcdef0;
218     pulBitsSrc[0] = 0x87684321;
219     pulBitsSrc[1] = 0x0fedcba9;
220     pjBitsMsk[0] = 0x80;
221     SetLastError(0xDEADBEEF);
222     ret = MaskBlt(hdcDst, 0, 0, 8, 1, hdcSrc, 0, 0, hbmMsk, 0, 0, MAKEROP4(SRCCOPY, 0xAA0000));
223     ok_err(0xDEADBEEF);
224     ok(ret == 1, "MaskBlt failed (%d)\n", ret);
225     ok (pulBitsDst[0] == 0x87684321, "pulBitsDst[0] == 0x%lx\n", pulBitsDst[0]);
226     ok (pulBitsDst[1] == 0x9abcdef0, "pulBitsDst[0] == 0x%lx\n", pulBitsDst[1]);
227 
228     pulBitsDst[0] = 0x12345678;
229     pulBitsDst[1] = 0x9abcdef0;
230     SetLastError(0xDEADBEEF);
231     ret = MaskBlt(hdcDst, 0, 0, 8, 1, hdcSrc, 0, 0, hbmMsk, 0, 0, MAKEROP4(SRCPAINT, MERGEPAINT));
232     ok_err(0xDEADBEEF);
233     ok(ret == 1, "MaskBlt failed (%d)\n", ret);
234     ok (pulBitsDst[0] == 0x977c5779, "pulBitsDst[0] == 0x%lx\n", pulBitsDst[0]);
235     ok (pulBitsDst[1] == 0xfabefef6, "pulBitsDst[0] == 0x%lx\n", pulBitsDst[1]);
236 }
237 
Test_MaskBlt_Brush()238 void Test_MaskBlt_Brush()
239 {
240     HDC hdcDst, hdcSrc;
241     struct
242     {
243         BITMAPINFOHEADER bmiHeader;
244         ULONG aulColors[2];
245     } bmiData = {{sizeof(BITMAPINFOHEADER), 16, 16, 1, 1, BI_RGB, 0, 10, 10, 2,0}, {0, 0xFFFFFF}};
246     PBITMAPINFO pbmi = (PBITMAPINFO)&bmiData;
247     HBITMAP hbmDst, hbmSrc, hbmMsk;
248     PULONG pulBitsDst, pulBitsSrc, pulBitsMsk;
249     BOOL ret;
250     HBRUSH hbr;
251 
252     /* Create a dest dc and bitmap */
253     hdcDst = CreateCompatibleDC(NULL);
254     hbmDst = CreateDIBSection(hdcDst, pbmi, DIB_RGB_COLORS, (PVOID*)&pulBitsDst, NULL, 0);
255     SelectObject(hdcDst, hbmDst);
256 
257     /* Create a source dc and bitmap */
258     hdcSrc = CreateCompatibleDC(NULL);
259     hbmSrc = CreateDIBSection(hdcSrc, pbmi, DIB_RGB_COLORS, (PVOID*)&pulBitsSrc, NULL, 0);
260     SelectObject(hdcSrc, hbmSrc);
261 
262     hbr = CreateHatchBrush(HS_CROSS, 0);
263     ok(hbr != 0, "failed to create brush\n");
264     ok(SelectObject(hdcDst, hbr) != 0, "failed to select brush\n");
265 
266     /* Do the masking (SRCCOPY / NOOP) */
267     pulBitsDst[0] = 0x00000000;
268     pulBitsSrc[0] = 0xFFFFFFFF;
269     SetLastError(0xDEADBEEF);
270     ret = MaskBlt(hdcDst, 0, 0, 8, 1, hdcSrc, 0, 0, NULL, 0, 0, MAKEROP4(SRCCOPY, 0xAA0000));
271     ok_err(0xDEADBEEF);
272     ok(ret == 1, "MaskBlt failed (%d)\n", ret);
273     ok(pulBitsDst[0] == 0, "pulBitsDst[0] == 0x%lx\n", pulBitsDst[0]);
274 
275     /* Create a 1 bpp pattern brush */
276     pbmi->bmiHeader.biWidth = 8;
277     hbmMsk = CreateDIBSection(hdcDst, pbmi, DIB_RGB_COLORS, (PVOID*)&pulBitsMsk, NULL, 0);
278     ok(hbmMsk != 0, "CreateDIBSection failed\n");
279     hbr = CreatePatternBrush(hbmMsk);
280     ok(hbr != 0, "CreatePatternBrush failed\n");
281     ok(SelectObject(hdcDst, hbr) != 0, "failed to select brush\n");
282 
283     /* Do the masking (SRCCOPY / NOOP) */
284     pulBitsDst[0] = 0x00000000;
285     pulBitsSrc[0] = 0xFFFFFFFF;
286     pulBitsMsk[0] = 0xCCAAFF00;
287     SetLastError(0xDEADBEEF);
288     ret = MaskBlt(hdcDst, 0, 0, 16, 1, hdcSrc, 0, 0, NULL, 0, 0, MAKEROP4(SRCCOPY, 0xAA0000));
289     ok_err(0xDEADBEEF);
290     ok(ret == 1, "MaskBlt failed (%d)\n", ret);
291     ok(pulBitsDst[0] == 0, "pulBitsDst[0] == 0x%lx\n", pulBitsDst[0]);
292 }
293 
START_TEST(MaskBlt)294 START_TEST(MaskBlt)
295 {
296     InitStuff();
297     Test_MaskBlt_1bpp();
298     Test_MaskBlt_16bpp();
299     Test_MaskBlt_32bpp();
300     Test_MaskBlt_Brush();
301 }
302