ReactOS 0.4.15-dev-6644-g539123c
dibobj.c
Go to the documentation of this file.
1/*
2 * PROJECT: ReactOS win32 kernel mode subsystem
3 * LICENSE: GPL - See COPYING in the top level directory
4 * FILE: win32ss/gdi/ntgdi/dibobj.c
5 * PURPOSE: Dib object functions
6 * PROGRAMMER:
7 */
8
9#include <win32k.h>
10
11#define NDEBUG
12#include <debug.h>
13
14static const RGBQUAD DefLogPaletteQuads[20] = /* Copy of Default Logical Palette */
15{
16 /* rgbBlue, rgbGreen, rgbRed, rgbReserved */
17 { 0x00, 0x00, 0x00, 0x00 },
18 { 0x00, 0x00, 0x80, 0x00 },
19 { 0x00, 0x80, 0x00, 0x00 },
20 { 0x00, 0x80, 0x80, 0x00 },
21 { 0x80, 0x00, 0x00, 0x00 },
22 { 0x80, 0x00, 0x80, 0x00 },
23 { 0x80, 0x80, 0x00, 0x00 },
24 { 0xc0, 0xc0, 0xc0, 0x00 },
25 { 0xc0, 0xdc, 0xc0, 0x00 },
26 { 0xf0, 0xca, 0xa6, 0x00 },
27 { 0xf0, 0xfb, 0xff, 0x00 },
28 { 0xa4, 0xa0, 0xa0, 0x00 },
29 { 0x80, 0x80, 0x80, 0x00 },
30 { 0x00, 0x00, 0xff, 0x00 },
31 { 0x00, 0xff, 0x00, 0x00 },
32 { 0x00, 0xff, 0xff, 0x00 },
33 { 0xff, 0x00, 0x00, 0x00 },
34 { 0xff, 0x00, 0xff, 0x00 },
35 { 0xff, 0xff, 0x00, 0x00 },
36 { 0xff, 0xff, 0xff, 0x00 }
37};
38
42 _In_ const BITMAPINFO *pbmi,
43 _In_ PDC pdc,
45{
46 PPALETTE ppal;
47 ULONG i, cBitsPixel, cColors;
48
50 {
52 cBitsPixel = pbci->bmciHeader.bcBitCount;
53 }
54 else
55 {
56 cBitsPixel = pbmi->bmiHeader.biBitCount;
57 }
58
59 /* Check if the colors are indexed */
60 if (cBitsPixel <= 8)
61 {
62 /* We create a "full" palette */
63 cColors = 1 << cBitsPixel;
64
65 /* Allocate the palette */
67 cColors,
68 NULL,
69 0,
70 0,
71 0);
72 if (ppal == NULL)
73 {
74 DPRINT1("Failed to allocate palette.\n");
75 return NULL;
76 }
77
78 /* Check if the BITMAPINFO specifies how many colors to use */
79 if ((pbmi->bmiHeader.biSize >= sizeof(BITMAPINFOHEADER)) &&
80 (pbmi->bmiHeader.biClrUsed != 0))
81 {
82 /* This is how many colors we can actually process */
83 cColors = min(cColors, pbmi->bmiHeader.biClrUsed);
84 }
85
86 /* Check how to use the colors */
88 {
89 COLORREF crColor;
90
91 /* The colors are an array of WORD indices into the DC palette */
92 PWORD pwColors = (PWORD)((PCHAR)pbmi + pbmi->bmiHeader.biSize);
93
94 /* Use the DCs palette or, if no DC is given, the default one */
95 PPALETTE ppalDC = pdc ? pdc->dclevel.ppal : gppalDefault;
96
97 /* Loop all color indices in the DIB */
98 for (i = 0; i < cColors; i++)
99 {
100 /* Get the palette index and handle wraparound when exceeding
101 the number of colors in the DC palette */
102 WORD wIndex = pwColors[i] % ppalDC->NumColors;
103
104 /* USe the RGB value from the DC palette */
105 crColor = PALETTE_ulGetRGBColorFromIndex(ppalDC, wIndex);
106 PALETTE_vSetRGBColorForIndex(ppal, i, crColor);
107 }
108 }
109 else if (iUsage == DIB_PAL_BRUSHHACK)
110 {
111 /* The colors are an array of WORD indices into the DC palette */
112 PWORD pwColors = (PWORD)((PCHAR)pbmi + pbmi->bmiHeader.biSize);
113
114 /* Loop all color indices in the DIB */
115 for (i = 0; i < cColors; i++)
116 {
117 /* Set the index directly as the RGB color, the real palette
118 containing RGB values will be calculated when the brush is
119 realized */
120 PALETTE_vSetRGBColorForIndex(ppal, i, pwColors[i]);
121 }
122
123 /* Mark the palette as a brush hack palette */
124 ppal->flFlags |= PAL_BRUSHHACK;
125 }
126// else if (iUsage == 2)
127// {
128 // FIXME: this one is undocumented
129// ASSERT(FALSE);
130// }
131 else if (pbmi->bmiHeader.biSize >= sizeof(BITMAPINFOHEADER))
132 {
133 /* The colors are an array of RGBQUAD values */
134 RGBQUAD *prgb = (RGBQUAD*)((PCHAR)pbmi + pbmi->bmiHeader.biSize);
135 RGBQUAD colors[256] = {{0}};
136
137 // FIXME: do we need to handle PALETTEINDEX / PALETTERGB macro?
138
139 /* Use SEH to verify we can READ prgb[] succesfully */
141 {
142 RtlCopyMemory(colors, prgb, cColors * sizeof(colors[0]));
143 }
145 {
146 /* Do Nothing */
147 }
148 _SEH2_END;
149
150 for (i = 0; i < cColors; ++i)
151 {
152 /* Get the color value and translate it to a COLORREF */
153 COLORREF crColor = RGB(colors[i].rgbRed, colors[i].rgbGreen, colors[i].rgbBlue);
154
155 /* Set the RGB value in the palette */
156 PALETTE_vSetRGBColorForIndex(ppal, i, crColor);
157 }
158 }
159 else
160 {
161 /* The colors are an array of RGBTRIPLE values */
163
164 /* Loop all color indices in the DIB */
165 for (i = 0; i < cColors; i++)
166 {
167 /* Get the color value and translate it to a COLORREF */
168 RGBTRIPLE rgb = prgb[i];
169 COLORREF crColor = RGB(rgb.rgbtRed, rgb.rgbtGreen, rgb.rgbtBlue);
170
171 /* Set the RGB value in the palette */
172 PALETTE_vSetRGBColorForIndex(ppal, i, crColor);
173 }
174 }
175 }
176 else
177 {
178 /* This is a bitfield / RGB palette */
179 ULONG flRedMask, flGreenMask, flBlueMask;
180
181 /* Check if the DIB contains bitfield values */
182 if ((pbmi->bmiHeader.biSize >= sizeof(BITMAPINFOHEADER)) &&
184 {
185 /* Check if we have a v4/v5 header */
186 if (pbmi->bmiHeader.biSize >= sizeof(BITMAPV4HEADER))
187 {
188 /* The masks are dedicated fields in the header */
190 flRedMask = pbmV4Header->bV4RedMask;
191 flGreenMask = pbmV4Header->bV4GreenMask;
192 flBlueMask = pbmV4Header->bV4BlueMask;
193 }
194 else
195 {
196 /* The masks are the first 3 values in the DIB color table */
197 PDWORD pdwColors = (PVOID)((PCHAR)pbmi + pbmi->bmiHeader.biSize);
198 flRedMask = pdwColors[0];
199 flGreenMask = pdwColors[1];
200 flBlueMask = pdwColors[2];
201 }
202 }
203 else
204 {
205 /* Check what bit depth we have. Note: optimization flags are
206 calculated in PALETTE_AllocPalette() */
207 if (cBitsPixel == 16)
208 {
209 /* This is an RGB 555 palette */
210 flRedMask = 0x7C00;
211 flGreenMask = 0x03E0;
212 flBlueMask = 0x001F;
213 }
214 else
215 {
216 /* This is an RGB 888 palette */
217 flRedMask = 0xFF0000;
218 flGreenMask = 0x00FF00;
219 flBlueMask = 0x0000FF;
220 }
221 }
222
223 /* Allocate the bitfield palette */
225 0,
226 NULL,
227 flRedMask,
228 flGreenMask,
229 flBlueMask);
230 }
231
232 /* We're done, return the palette */
233 return ppal;
234}
235
236// Converts a DIB to a device-dependent bitmap
237static INT
240 PDC DC,
242 UINT StartScan,
243 UINT ScanLines,
244 CONST VOID *Bits,
246 CONST BITMAPINFO *bmi,
247 UINT ColorUse)
248{
249 HBITMAP SourceBitmap;
250 PSURFACE psurfDst, psurfSrc;
251 INT result = 0;
252 RECT rcDst;
253 POINTL ptSrc;
254 EXLATEOBJ exlo;
255 PPALETTE ppalDIB = 0;
256 ULONG cjSizeImage;
257
258 if (!bmi || !Bits) return 0;
259
260 /* Check for uncompressed formats */
261 if ((bmi->bmiHeader.biCompression == BI_RGB) ||
262 (bmi->bmiHeader.biCompression == BI_BITFIELDS))
263 {
264 /* Calculate the image size */
265 cjSizeImage = DIB_GetDIBImageBytes(bmi->bmiHeader.biWidth,
266 ScanLines,
267 bmi->bmiHeader.biBitCount);
268 }
269 /* Check if the header provided an image size */
270 else if (bmi->bmiHeader.biSizeImage != 0)
271 {
272 /* Use the given size */
273 cjSizeImage = bmi->bmiHeader.biSizeImage;
274 }
275 else
276 {
277 /* Compressed format without a size. This is invalid. */
278 DPRINT1("Compressed format without a size!");
279 return 0;
280 }
281
282 /* Check if the size that we have is ok */
283 if ((cjSizeImage > cjMaxBits) || (cjSizeImage == 0))
284 {
285 DPRINT1("Invalid bitmap size! cjSizeImage = %lu, cjMaxBits = %lu\n",
286 cjSizeImage, cjMaxBits);
287 return 0;
288 }
289
290 SourceBitmap = GreCreateBitmapEx(bmi->bmiHeader.biWidth,
291 ScanLines,
292 0,
293 BitmapFormat(bmi->bmiHeader.biBitCount,
294 bmi->bmiHeader.biCompression),
295 bmi->bmiHeader.biHeight < 0 ? BMF_TOPDOWN : 0,
296 cjSizeImage,
297 (PVOID)Bits,
298 0);
299 if (!SourceBitmap)
300 {
301 DPRINT1("Error: Could not create a bitmap.\n");
303 return 0;
304 }
305
307 psurfSrc = SURFACE_ShareLockSurface(SourceBitmap);
308
309 if(!(psurfSrc && psurfDst))
310 {
311 DPRINT1("Error: Could not lock surfaces\n");
312 goto cleanup;
313 }
314
315 /* Create a palette for the DIB */
316 ppalDIB = CreateDIBPalette(bmi, DC, ColorUse);
317 if (!ppalDIB)
318 {
320 goto cleanup;
321 }
322
323 /* Initialize EXLATEOBJ */
325 ppalDIB,
326 psurfDst->ppal,
327 RGB(0xff, 0xff, 0xff),
328 RGB(0xff, 0xff, 0xff), //DC->pdcattr->crBackgroundClr,
329 0); // DC->pdcattr->crForegroundClr);
330
331 rcDst.top = StartScan;
332 rcDst.left = 0;
333 rcDst.bottom = rcDst.top + ScanLines;
334 rcDst.right = psurfDst->SurfObj.sizlBitmap.cx;
335 ptSrc.x = 0;
336 ptSrc.y = 0;
337
338 result = IntEngCopyBits(&psurfDst->SurfObj,
339 &psurfSrc->SurfObj,
340 NULL,
341 &exlo.xlo,
342 &rcDst,
343 &ptSrc);
344 if(result)
345 result = ScanLines;
346
347 EXLATEOBJ_vCleanup(&exlo);
348
349cleanup:
350 if (ppalDIB) PALETTE_ShareUnlockPalette(ppalDIB);
351 if(psurfSrc) SURFACE_ShareUnlockSurface(psurfSrc);
352 if(psurfDst) SURFACE_ShareUnlockSurface(psurfDst);
353 GreDeleteObject(SourceBitmap);
354
355 return result;
356}
357
358static
361 DWORD Width,
363 ULONG Compression,
364 const BYTE* Bits,
365 DWORD BitsSize)
366{
368 DWORD x, y;
369 SURFOBJ* SurfObj;
370 UINT i = 0;
371 BYTE Data, NumPixels, ToSkip;
372
373 ASSERT((Compression == BI_RLE8) || (Compression == BI_RLE4));
374
375 /* Create the bitmap */
377 if (!Mask)
378 return NULL;
379
380 SurfObj = EngLockSurface((HSURF)Mask);
381 if (!SurfObj)
382 {
384 return NULL;
385 }
386 ASSERT(SurfObj->pvBits != NULL);
387
388 x = y = 0;
389
390 while (i < BitsSize)
391 {
392 NumPixels = Bits[i];
393 Data = Bits[i + 1];
394 i += 2;
395
396 if (NumPixels != 0)
397 {
398 if ((x + NumPixels) > Width)
399 NumPixels = Width - x;
400
401 if (NumPixels == 0)
402 continue;
403
404 DIB_1BPP_HLine(SurfObj, x, x + NumPixels, y, 1);
405 x += NumPixels;
406 continue;
407 }
408
409 if (Data < 3)
410 {
411 switch (Data)
412 {
413 case 0:
414 /* End of line */
415 y++;
416 if (y == Height)
417 goto done;
418 x = 0;
419 break;
420 case 1:
421 /* End of file */
422 goto done;
423 case 2:
424 /* Jump */
425 if (i >= (BitsSize - 1))
426 goto done;
427 x += Bits[i];
428 if (x > Width)
429 x = Width;
430 y += Bits[i + 1];
431 if (y >= Height)
432 goto done;
433 i += 2;
434 break;
435 }
436 /* Done for this run */
437 continue;
438 }
439
440 /* Embedded data into the RLE */
441 NumPixels = Data;
442 if (Compression == BI_RLE8)
443 ToSkip = NumPixels;
444 else
445 ToSkip = (NumPixels / 2) + (NumPixels & 1);
446
447 if ((i + ToSkip) > BitsSize)
448 goto done;
449 ToSkip = (ToSkip + 1) & ~1;
450
451 if ((x + NumPixels) > Width)
452 NumPixels = Width - x;
453
454 if (NumPixels != 0)
455 {
456 DIB_1BPP_HLine(SurfObj, x, x + NumPixels, y, 1);
457 x += NumPixels;
458 }
459 i += ToSkip;
460 }
461
462done:
463 EngUnlockSurface(SurfObj);
464 return Mask;
465}
466
468INT
471 IN HDC hDC,
472 IN INT XDest,
473 IN INT YDest,
474 IN DWORD Width,
476 IN INT XSrc,
477 IN INT YSrc,
478 IN DWORD StartScan,
479 IN DWORD ScanLines,
480 IN LPBYTE Bits,
481 IN LPBITMAPINFO bmi,
482 IN DWORD ColorUse,
485 IN BOOL bTransformCoordinates,
487{
488 INT ret;
489 PDC pDC = NULL;
490 HBITMAP hSourceBitmap = NULL, hMaskBitmap = NULL;
491 SURFOBJ *pDestSurf, *pSourceSurf = NULL, *pMaskSurf = NULL;
492 SURFACE *pSurf;
493 RECTL rcDest;
494 POINTL ptSource;
495 //INT DIBWidth;
496 SIZEL SourceSize;
497 EXLATEOBJ exlo;
498 PPALETTE ppalDIB = NULL;
499 LPBITMAPINFO pbmiSafe;
500 BOOL bResult;
501
502 if (!Bits) return 0;
503
504 pbmiSafe = ExAllocatePoolWithTag(PagedPool, cjMaxInfo, 'pmTG');
505 if (!pbmiSafe) return 0;
506
508 {
509 ProbeForRead(bmi, cjMaxInfo, 1);
510 ProbeForRead(Bits, cjMaxBits, 1);
511 RtlCopyMemory(pbmiSafe, bmi, cjMaxInfo);
512 bmi = pbmiSafe;
513 }
515 {
516 ret = 0;
517 goto Exit;
518 }
519 _SEH2_END;
520
521 DPRINT("StartScan %d ScanLines %d Bits %p bmi %p ColorUse %d\n"
522 " Height %d Width %d SizeImage %d\n"
523 " biHeight %d biWidth %d biBitCount %d\n"
524 " XSrc %d YSrc %d xDext %d yDest %d\n",
525 StartScan, ScanLines, Bits, bmi, ColorUse,
526 Height, Width, bmi->bmiHeader.biSizeImage,
527 bmi->bmiHeader.biHeight, bmi->bmiHeader.biWidth,
528 bmi->bmiHeader.biBitCount,
529 XSrc, YSrc, XDest, YDest);
530
531 if (YDest >= 0)
532 {
533 ScanLines = min(abs(Height), ScanLines);
534 if (YSrc > 0)
535 ScanLines += YSrc;
536 }
537 else
538 {
539 ScanLines = min(ScanLines, abs(bmi->bmiHeader.biHeight) - StartScan);
540 }
541
542 if (ScanLines == 0)
543 {
544 DPRINT1("ScanLines == 0\n");
545 ret = 0;
546 goto Exit;
547 }
548
549 pDC = DC_LockDc(hDC);
550 if (!pDC)
551 {
553 ret = 0;
554 goto Exit;
555 }
556
557 if (pDC->dctype == DCTYPE_INFO)
558 {
559 ret = 0;
560 goto Exit;
561 }
562
563 rcDest.left = XDest;
564 rcDest.top = YDest;
565 if (bTransformCoordinates)
566 {
567 IntLPtoDP(pDC, (LPPOINT)&rcDest, 2);
568 }
569 rcDest.left += pDC->ptlDCOrig.x;
570 rcDest.top += pDC->ptlDCOrig.y;
571 rcDest.right = rcDest.left + Width;
572 rcDest.bottom = rcDest.top + Height;
573 rcDest.top += StartScan;
574
575 if (pDC->fs & (DC_ACCUM_APP|DC_ACCUM_WMGR))
576 {
577 IntUpdateBoundsRect(pDC, &rcDest);
578 }
579
580 ptSource.x = XSrc;
581 ptSource.y = YSrc;
582
583 SourceSize.cx = bmi->bmiHeader.biWidth;
584 SourceSize.cy = ScanLines;
585 if (YDest >= 0 && YSrc > 0)
586 {
587 ScanLines += YSrc;
588 }
589
590 //DIBWidth = WIDTH_BYTES_ALIGN32(SourceSize.cx, bmi->bmiHeader.biBitCount);
591
592 hSourceBitmap = GreCreateBitmapEx(bmi->bmiHeader.biWidth,
593 ScanLines,
594 0,
595 BitmapFormat(bmi->bmiHeader.biBitCount,
596 bmi->bmiHeader.biCompression),
597 bmi->bmiHeader.biHeight < 0 ? BMF_TOPDOWN : 0,
598 bmi->bmiHeader.biSizeImage,
599 Bits,
600 0);
601
602 if (!hSourceBitmap)
603 {
605 ret = 0;
606 goto Exit;
607 }
608
609 pSourceSurf = EngLockSurface((HSURF)hSourceBitmap);
610 if (!pSourceSurf)
611 {
612 ret = 0;
613 goto Exit;
614 }
615
616 /* HACK: If this is a RLE bitmap, only the relevant pixels must be set. */
617 if ((bmi->bmiHeader.biCompression == BI_RLE8) || (bmi->bmiHeader.biCompression == BI_RLE4))
618 {
619 hMaskBitmap = IntGdiCreateMaskFromRLE(bmi->bmiHeader.biWidth,
620 ScanLines,
621 bmi->bmiHeader.biCompression,
622 Bits,
623 cjMaxBits);
624 if (!hMaskBitmap)
625 {
627 ret = 0;
628 goto Exit;
629 }
630 pMaskSurf = EngLockSurface((HSURF)hMaskBitmap);
631 if (!pMaskSurf)
632 {
633 ret = 0;
634 goto Exit;
635 }
636 }
637
638 /* Create a palette for the DIB */
639 ppalDIB = CreateDIBPalette(bmi, pDC, ColorUse);
640 if (!ppalDIB)
641 {
643 ret = 0;
644 goto Exit;
645 }
646
647 /* This is actually a blit */
648 DC_vPrepareDCsForBlit(pDC, &rcDest, NULL, NULL);
649 pSurf = pDC->dclevel.pSurface;
650 if (!pSurf)
651 {
652 DC_vFinishBlit(pDC, NULL);
653 ret = ScanLines;
654 goto Exit;
655 }
656
657 ASSERT(pSurf->ppal);
658
659 /* Initialize EXLATEOBJ */
661 ppalDIB,
662 pSurf->ppal,
663 RGB(0xff, 0xff, 0xff),
664 pDC->pdcattr->crBackgroundClr,
665 pDC->pdcattr->crForegroundClr);
666
667 pDestSurf = &pSurf->SurfObj;
668
669 /* Copy the bits */
670 DPRINT("BitsToDev with rcDest=(%d|%d) (%d|%d), ptSource=(%d|%d) w=%d h=%d\n",
671 rcDest.left, rcDest.top, rcDest.right, rcDest.bottom,
672 ptSource.x, ptSource.y, SourceSize.cx, SourceSize.cy);
673
674 /* This fixes the large Google text on Google.com from being upside down */
675 if (rcDest.top > rcDest.bottom)
676 {
677 RECTL_vMakeWellOrdered(&rcDest);
678 ptSource.y -= SourceSize.cy;
679 }
680
681 bResult = IntEngBitBlt(pDestSurf,
682 pSourceSurf,
683 pMaskSurf,
684 (CLIPOBJ *)&pDC->co,
685 &exlo.xlo,
686 &rcDest,
687 &ptSource,
688 pMaskSurf ? &ptSource : NULL,
689 NULL,
690 NULL,
692
693 /* Cleanup EXLATEOBJ */
694 EXLATEOBJ_vCleanup(&exlo);
695
696 /* We're done */
697 DC_vFinishBlit(pDC, NULL);
698
699 ret = bResult ? ScanLines : 0;
700
701Exit:
702
703 if (ppalDIB) PALETTE_ShareUnlockPalette(ppalDIB);
704 if (pSourceSurf) EngUnlockSurface(pSourceSurf);
705 if (hSourceBitmap) EngDeleteSurface((HSURF)hSourceBitmap);
706 if (pMaskSurf) EngUnlockSurface(pMaskSurf);
707 if (hMaskBitmap) EngDeleteSurface((HSURF)hMaskBitmap);
708 if (pDC) DC_UnlockDc(pDC);
709 ExFreePoolWithTag(pbmiSafe, 'pmTG');
710
711 return ret;
712}
713
714
715/* Converts a device-dependent bitmap to a DIB */
716INT
719 HDC hDC,
721 UINT StartScan,
722 UINT ScanLines,
723 LPBYTE Bits,
725 UINT Usage,
726 UINT MaxBits,
727 UINT MaxInfo)
728{
729 BITMAPCOREINFO* pbmci = NULL;
730 PSURFACE psurf = NULL;
731 PDC pDC;
733 WORD planes, bpp;
734 DWORD compr, size ;
735 USHORT i;
736 int bitmap_type;
737 RGBQUAD* rgbQuads;
738 VOID* colorPtr;
739
740 DPRINT("Entered GreGetDIBitsInternal()\n");
741
742 if ((Usage && Usage != DIB_PAL_COLORS) || !Info || !hBitmap)
743 return 0;
744
745 pDC = DC_LockDc(hDC);
746 if (pDC == NULL || pDC->dctype == DCTYPE_INFO)
747 {
748 ScanLines = 0;
749 goto done;
750 }
751
752 /* Get a pointer to the source bitmap object */
754 if (psurf == NULL)
755 {
756 ScanLines = 0;
757 goto done;
758 }
759
760 colorPtr = (LPBYTE)Info + Info->bmiHeader.biSize;
761 rgbQuads = colorPtr;
762
763 bitmap_type = DIB_GetBitmapInfo(&Info->bmiHeader,
764 &width,
765 &height,
766 &planes,
767 &bpp,
768 &compr,
769 &size);
770 if(bitmap_type == -1)
771 {
772 DPRINT1("Wrong bitmap format\n");
774 ScanLines = 0;
775 goto done;
776 }
777 else if(bitmap_type == 0)
778 {
779 /* We need a BITMAPINFO to create a DIB, but we have to fill
780 * the BITMAPCOREINFO we're provided */
781 pbmci = (BITMAPCOREINFO*)Info;
782 /* fill in the the bit count, so we can calculate the right ColorsSize during the conversion */
785 if(Info == NULL)
786 {
787 DPRINT1("Error, could not convert the BITMAPCOREINFO!\n");
788 ScanLines = 0;
789 goto done;
790 }
791 rgbQuads = Info->bmiColors;
792 }
793
794 /* Validate input:
795 - negative width is always an invalid value
796 - non-null Bits and zero bpp is an invalid combination
797 - only check the rest of the input params if either bpp is non-zero or Bits are set */
798 if (width < 0 || (bpp == 0 && Bits))
799 {
800 ScanLines = 0;
801 goto done;
802 }
803
804 if (Bits || bpp)
805 {
806 if ((height == 0 || width == 0) || (compr && compr != BI_BITFIELDS && compr != BI_RGB))
807 {
808 ScanLines = 0;
809 goto done;
810 }
811 }
812
813 Info->bmiHeader.biClrUsed = 0;
814 Info->bmiHeader.biClrImportant = 0;
815
816 /* Fill in the structure */
817 switch(bpp)
818 {
819 case 0: /* Only info */
820 Info->bmiHeader.biWidth = psurf->SurfObj.sizlBitmap.cx;
821 Info->bmiHeader.biHeight = (psurf->SurfObj.fjBitmap & BMF_TOPDOWN) ?
822 -psurf->SurfObj.sizlBitmap.cy :
823 psurf->SurfObj.sizlBitmap.cy;
824 Info->bmiHeader.biPlanes = 1;
825 Info->bmiHeader.biBitCount = BitsPerFormat(psurf->SurfObj.iBitmapFormat);
826 Info->bmiHeader.biSizeImage = DIB_GetDIBImageBytes( Info->bmiHeader.biWidth,
827 Info->bmiHeader.biHeight,
828 Info->bmiHeader.biBitCount);
829 Info->bmiHeader.biCompression = (Info->bmiHeader.biBitCount == 16 || Info->bmiHeader.biBitCount == 32) ?
831 Info->bmiHeader.biXPelsPerMeter = 0;
832 Info->bmiHeader.biYPelsPerMeter = 0;
833
834 if (Info->bmiHeader.biBitCount <= 8 && Info->bmiHeader.biClrUsed == 0)
835 Info->bmiHeader.biClrUsed = 1 << Info->bmiHeader.biBitCount;
836
837 ScanLines = 1;
838 goto done;
839
840 case 1:
841 case 4:
842 case 8:
843 Info->bmiHeader.biClrUsed = 1 << bpp;
844
845 /* If the bitmap is a DIB section and has the same format as what
846 * is requested, go ahead! */
847 if((psurf->hSecure) &&
849 {
850 if(Usage == DIB_RGB_COLORS)
851 {
852 ULONG colors = min(psurf->ppal->NumColors, 256);
853 if(colors != 256) Info->bmiHeader.biClrUsed = colors;
854 for(i = 0; i < colors; i++)
855 {
856 rgbQuads[i].rgbRed = psurf->ppal->IndexedColors[i].peRed;
857 rgbQuads[i].rgbGreen = psurf->ppal->IndexedColors[i].peGreen;
858 rgbQuads[i].rgbBlue = psurf->ppal->IndexedColors[i].peBlue;
859 rgbQuads[i].rgbReserved = 0;
860 }
861 }
862 else
863 {
864 for(i = 0; i < 256; i++)
865 ((WORD*)rgbQuads)[i] = i;
866 }
867 }
868 else
869 {
870 if(Usage == DIB_PAL_COLORS)
871 {
872 for(i = 0; i < 256; i++)
873 {
874 ((WORD*)rgbQuads)[i] = i;
875 }
876 }
877 else if(bpp > 1 && bpp == BitsPerFormat(psurf->SurfObj.iBitmapFormat))
878 {
879 /* For color DDBs in native depth (mono DDBs always have
880 a black/white palette):
881 Generate the color map from the selected palette */
882 PPALETTE pDcPal = PALETTE_ShareLockPalette(pDC->dclevel.hpal);
883 if(!pDcPal)
884 {
885 ScanLines = 0 ;
886 goto done ;
887 }
888 for (i = 0; i < pDcPal->NumColors; i++)
889 {
890 rgbQuads[i].rgbRed = pDcPal->IndexedColors[i].peRed;
891 rgbQuads[i].rgbGreen = pDcPal->IndexedColors[i].peGreen;
892 rgbQuads[i].rgbBlue = pDcPal->IndexedColors[i].peBlue;
893 rgbQuads[i].rgbReserved = 0;
894 }
896 }
897 else
898 {
899 switch (bpp)
900 {
901 case 1:
902 rgbQuads[0].rgbRed = rgbQuads[0].rgbGreen = rgbQuads[0].rgbBlue = 0;
903 rgbQuads[0].rgbReserved = 0;
904 rgbQuads[1].rgbRed = rgbQuads[1].rgbGreen = rgbQuads[1].rgbBlue = 0xff;
905 rgbQuads[1].rgbReserved = 0;
906 break;
907
908 case 4:
909 /* The EGA palette is the first and last 8 colours of the default palette
910 with the innermost pair swapped */
911 RtlCopyMemory(rgbQuads, DefLogPaletteQuads, 7 * sizeof(RGBQUAD));
912 RtlCopyMemory(rgbQuads + 7, DefLogPaletteQuads + 12, 1 * sizeof(RGBQUAD));
913 RtlCopyMemory(rgbQuads + 8, DefLogPaletteQuads + 7, 1 * sizeof(RGBQUAD));
914 RtlCopyMemory(rgbQuads + 9, DefLogPaletteQuads + 13, 7 * sizeof(RGBQUAD));
915 break;
916
917 case 8:
918 {
919 INT i;
920
921 memcpy(rgbQuads, DefLogPaletteQuads, 10 * sizeof(RGBQUAD));
922 memcpy(rgbQuads + 246, DefLogPaletteQuads + 10, 10 * sizeof(RGBQUAD));
923
924 for (i = 10; i < 246; i++)
925 {
926 rgbQuads[i].rgbRed = (i & 0x07) << 5;
927 rgbQuads[i].rgbGreen = (i & 0x38) << 2;
928 rgbQuads[i].rgbBlue = i & 0xc0;
929 rgbQuads[i].rgbReserved = 0;
930 }
931 }
932 }
933 }
934 }
935 break;
936
937 case 15:
938 if (Info->bmiHeader.biCompression == BI_BITFIELDS)
939 {
940 ((PDWORD)Info->bmiColors)[0] = 0x7c00;
941 ((PDWORD)Info->bmiColors)[1] = 0x03e0;
942 ((PDWORD)Info->bmiColors)[2] = 0x001f;
943 }
944 break;
945
946 case 16:
947 if (Info->bmiHeader.biCompression == BI_BITFIELDS)
948 {
949 if (psurf->hSecure)
950 {
951 ((PDWORD)Info->bmiColors)[0] = psurf->ppal->RedMask;
952 ((PDWORD)Info->bmiColors)[1] = psurf->ppal->GreenMask;
953 ((PDWORD)Info->bmiColors)[2] = psurf->ppal->BlueMask;
954 }
955 else
956 {
957 ((PDWORD)Info->bmiColors)[0] = 0xf800;
958 ((PDWORD)Info->bmiColors)[1] = 0x07e0;
959 ((PDWORD)Info->bmiColors)[2] = 0x001f;
960 }
961 }
962 break;
963
964 case 24:
965 case 32:
966 if (Info->bmiHeader.biCompression == BI_BITFIELDS)
967 {
968 if (psurf->hSecure)
969 {
970 ((PDWORD)Info->bmiColors)[0] = psurf->ppal->RedMask;
971 ((PDWORD)Info->bmiColors)[1] = psurf->ppal->GreenMask;
972 ((PDWORD)Info->bmiColors)[2] = psurf->ppal->BlueMask;
973 }
974 else
975 {
976 ((PDWORD)Info->bmiColors)[0] = 0xff0000;
977 ((PDWORD)Info->bmiColors)[1] = 0x00ff00;
978 ((PDWORD)Info->bmiColors)[2] = 0x0000ff;
979 }
980 }
981 break;
982
983 default:
984 ScanLines = 0;
985 goto done;
986 }
987
988 Info->bmiHeader.biSizeImage = DIB_GetDIBImageBytes(width, height, bpp);
989 Info->bmiHeader.biPlanes = 1;
990
991 if(Bits && ScanLines)
992 {
993 /* Create a DIBSECTION, blt it, profit */
994 PVOID pDIBits ;
995 HBITMAP hBmpDest;
996 PSURFACE psurfDest;
997 EXLATEOBJ exlo;
998 RECT rcDest;
999 POINTL srcPoint;
1000 BOOL ret ;
1001 int newLines = -1;
1002
1003 if (StartScan >= abs(Info->bmiHeader.biHeight))
1004 {
1005 ScanLines = 1;
1006 goto done;
1007 }
1008 else
1009 {
1010 ScanLines = min(ScanLines, abs(Info->bmiHeader.biHeight) - StartScan);
1011 }
1012
1013 if (abs(Info->bmiHeader.biHeight) < psurf->SurfObj.sizlBitmap.cy)
1014 {
1015 StartScan += psurf->SurfObj.sizlBitmap.cy - abs(Info->bmiHeader.biHeight);
1016 }
1017 /* Fixup values */
1018 Info->bmiHeader.biHeight = (height < 0) ?
1019 -(LONG)ScanLines : ScanLines;
1020 /* Create the DIB */
1021 hBmpDest = DIB_CreateDIBSection(pDC, Info, Usage, &pDIBits, NULL, 0, 0);
1022 /* Restore them */
1023 Info->bmiHeader.biHeight = height;
1024
1025 if(!hBmpDest)
1026 {
1027 DPRINT1("Unable to create a DIB Section!\n");
1029 ScanLines = 0;
1030 goto done ;
1031 }
1032
1033 psurfDest = SURFACE_ShareLockSurface(hBmpDest);
1034
1035 RECTL_vSetRect(&rcDest, 0, 0, Info->bmiHeader.biWidth, ScanLines);
1036 Info->bmiHeader.biWidth = width;
1037 srcPoint.x = 0;
1038
1039 if (abs(Info->bmiHeader.biHeight) <= psurf->SurfObj.sizlBitmap.cy)
1040 {
1041 srcPoint.y = psurf->SurfObj.sizlBitmap.cy - StartScan - ScanLines;
1042 }
1043 else
1044 {
1045 /* Determine the actual number of lines copied from the */
1046 /* original bitmap. It might be different from ScanLines. */
1047 newLines = abs(Info->bmiHeader.biHeight) - psurf->SurfObj.sizlBitmap.cy;
1048 newLines = min((int)(StartScan + ScanLines - newLines), psurf->SurfObj.sizlBitmap.cy);
1049 if (newLines > 0)
1050 {
1051 srcPoint.y = psurf->SurfObj.sizlBitmap.cy - newLines;
1052 if (StartScan > psurf->SurfObj.sizlBitmap.cy)
1053 {
1054 newLines -= (StartScan - psurf->SurfObj.sizlBitmap.cy);
1055 }
1056 }
1057 else
1058 {
1059 newLines = 0;
1060 srcPoint.y = psurf->SurfObj.sizlBitmap.cy;
1061 }
1062 }
1063
1064 EXLATEOBJ_vInitialize(&exlo, psurf->ppal, psurfDest->ppal, 0xffffff, 0xffffff, 0);
1065
1066 ret = IntEngCopyBits(&psurfDest->SurfObj,
1067 &psurf->SurfObj,
1068 NULL,
1069 &exlo.xlo,
1070 &rcDest,
1071 &srcPoint);
1072
1073 SURFACE_ShareUnlockSurface(psurfDest);
1074
1075 if(!ret)
1076 ScanLines = 0;
1077 else
1078 {
1079 RtlCopyMemory(Bits, pDIBits, DIB_GetDIBImageBytes (width, ScanLines, bpp));
1080 }
1081 /* Update if line count has changed */
1082 if (newLines != -1)
1083 {
1084 ScanLines = (UINT)newLines;
1085 }
1086 GreDeleteObject(hBmpDest);
1087 EXLATEOBJ_vCleanup(&exlo);
1088 }
1089 else
1090 {
1091 /* Signals success and not the actual number of scan lines*/
1092 ScanLines = 1;
1093 }
1094
1095done:
1096
1097 if (pbmci)
1099
1100 if (psurf)
1102
1103 if (pDC)
1104 DC_UnlockDc(pDC);
1105
1106 return ScanLines;
1107}
1108
1109_Success_(return!=0)
1111INT
1113NtGdiGetDIBitsInternal(
1114 _In_ HDC hdc,
1123{
1124 PBITMAPINFO pbmiSafe;
1125 HANDLE hSecure = NULL;
1126 INT iResult = 0;
1127 UINT cjAlloc;
1128
1129 /* Check for bad iUsage */
1130 if (iUsage > 2) return 0;
1131
1132 /* Check if the size of the bitmap info is large enough */
1133 if (cjMaxInfo < sizeof(BITMAPCOREHEADER))
1134 {
1135 return 0;
1136 }
1137
1138 /* Use maximum size */
1139 cjMaxInfo = min(cjMaxInfo, sizeof(BITMAPV5HEADER) + 256 * sizeof(RGBQUAD));
1140
1141 // HACK: the underlying code sucks and doesn't care for the size, so we
1142 // give it the maximum ever needed
1143 cjAlloc = sizeof(BITMAPV5HEADER) + 256 * sizeof(RGBQUAD);
1144
1145 /* Allocate a buffer the bitmapinfo */
1146 pbmiSafe = ExAllocatePoolWithTag(PagedPool, cjAlloc, 'imBG');
1147 if (!pbmiSafe)
1148 {
1149 /* Fail */
1150 return 0;
1151 }
1152
1153 /* Use SEH */
1154 _SEH2_TRY
1155 {
1156 /* Probe and copy the BITMAPINFO */
1158 RtlCopyMemory(pbmiSafe, pbmi, cjMaxInfo);
1159 }
1161 {
1162 goto cleanup;
1163 }
1164 _SEH2_END;
1165
1166 /* Check if the header size is large enough */
1167 if ((pbmiSafe->bmiHeader.biSize < sizeof(BITMAPCOREHEADER)) ||
1168 (pbmiSafe->bmiHeader.biSize > cjMaxInfo))
1169 {
1170 goto cleanup;
1171 }
1172
1173 /* Check if the caller provided bitmap bits */
1174 if (pjBits)
1175 {
1176 /* Secure the user mode memory */
1177 hSecure = EngSecureMem(pjBits, cjMaxBits);
1178 if (!hSecure)
1179 {
1180 goto cleanup;
1181 }
1182 }
1183
1184 /* Now call the internal function */
1185 iResult = GreGetDIBitsInternal(hdc,
1186 hbm,
1187 iStartScan,
1188 cScans,
1189 pjBits,
1190 pbmiSafe,
1191 iUsage,
1192 cjMaxBits,
1193 cjMaxInfo);
1194
1195 /* Check for success */
1196 if (iResult)
1197 {
1198 /* Use SEH to copy back to user mode */
1199 _SEH2_TRY
1200 {
1201 /* Copy the data back */
1204 RtlCopyMemory(pbmi, pbmiSafe, cjMaxInfo);
1205 }
1207 {
1208 /* Ignore */
1209 (VOID)0;
1210 }
1211 _SEH2_END;
1212 }
1213
1214cleanup:
1215 if (hSecure) EngUnsecureMem(hSecure);
1216 ExFreePoolWithTag(pbmiSafe, 'imBG');
1217
1218 return iResult;
1219}
1220
1221
1222W32KAPI
1223INT
1226 IN HDC hdc,
1227 IN INT xDst,
1228 IN INT yDst,
1229 IN INT cxDst,
1230 IN INT cyDst,
1231 IN INT xSrc,
1232 IN INT ySrc,
1233 IN INT cxSrc,
1234 IN INT cySrc,
1235 IN OPTIONAL LPBYTE pjInit,
1237 IN DWORD dwUsage,
1238 IN DWORD dwRop, // MS ntgdi.h says dwRop4(?)
1242{
1243 SIZEL sizel;
1244 RECTL rcSrc, rcDst;
1245 PDC pdc;
1246 HBITMAP hbmTmp = 0;
1247 PSURFACE psurfTmp = 0, psurfDst = 0;
1248 PPALETTE ppalDIB = 0;
1249 EXLATEOBJ exlo;
1250 PBYTE pvBits;
1251
1252 LPBITMAPINFO pbmiSafe;
1253 UINT cjAlloc;
1254 HBITMAP hBitmap, hOldBitmap = NULL;
1255 HDC hdcMem;
1256 HPALETTE hPal = NULL;
1257 ULONG BmpFormat = 0;
1258 INT LinesCopied = 0;
1259
1260 /* Check for bad iUsage */
1261 if (dwUsage > 2) return 0;
1262
1263 /* We must have LPBITMAPINFO */
1264 if (!pbmi)
1265 {
1266 DPRINT1("Error, Invalid Parameter.\n");
1268 return 0;
1269 }
1270
1271 /* Check if the size of the bitmap info is large enough */
1272 if (cjMaxInfo < sizeof(BITMAPCOREHEADER))
1273 {
1274 return 0;
1275 }
1276
1277 /* Use maximum size */
1278 cjMaxInfo = min(cjMaxInfo, sizeof(BITMAPV5HEADER) + 256 * sizeof(RGBQUAD));
1279
1280 // HACK: the underlying code sucks and doesn't care for the size, so we
1281 // give it the maximum ever needed
1282 cjAlloc = sizeof(BITMAPV5HEADER) + 256 * sizeof(RGBQUAD);
1283
1284 /* Allocate a buffer the bitmapinfo */
1285 pbmiSafe = ExAllocatePoolWithTag(PagedPool, cjAlloc, 'imBG');
1286 if (!pbmiSafe)
1287 {
1288 /* Fail */
1289 return 0;
1290 }
1291
1292 /* Use SEH */
1293 _SEH2_TRY
1294 {
1295 /* Probe and copy the BITMAPINFO */
1297 RtlCopyMemory(pbmiSafe, pbmi, cjMaxInfo);
1298 }
1300 {
1301 ExFreePoolWithTag(pbmiSafe, 'imBG');
1302 return 0;
1303 }
1304 _SEH2_END;
1305
1306 /* Check if the header size is large enough */
1307 if ((pbmiSafe->bmiHeader.biSize < sizeof(BITMAPCOREHEADER)) ||
1308 (pbmiSafe->bmiHeader.biSize > cjMaxInfo))
1309 {
1310 ExFreePoolWithTag(pbmiSafe, 'imBG');
1311 return 0;
1312 }
1313
1314 if (!(pdc = DC_LockDc(hdc)))
1315 {
1317 return 0;
1318 }
1319
1320 /* Check for info / mem DC without surface */
1321 if (!pdc->dclevel.pSurface)
1322 {
1323 DC_UnlockDc(pdc);
1324 // CHECKME
1325 return TRUE;
1326 }
1327
1328 /* Transform dest size */
1329 sizel.cx = cxDst;
1330 sizel.cy = cyDst;
1331 IntLPtoDP(pdc, (POINTL*)&sizel, 1);
1332 DC_UnlockDc(pdc);
1333
1334 if (pjInit && (cjMaxBits > 0))
1335 {
1337 if (!pvBits)
1338 {
1339 return 0;
1340 }
1341
1342 _SEH2_TRY
1343 {
1344 ProbeForRead(pjInit, cjMaxBits, 1);
1345 RtlCopyMemory(pvBits, pjInit, cjMaxBits);
1346 }
1348 {
1349 ExFreePoolWithTag(pvBits, TAG_DIB);
1350 return 0;
1351 }
1352 _SEH2_END;
1353 }
1354 else
1355 {
1356 pvBits = NULL;
1357 }
1358
1359 /* Here we select between the dwRop with SRCCOPY or not. */
1360 if (dwRop == SRCCOPY)
1361 {
1363 if (hdcMem == NULL)
1364 {
1365 DPRINT1("NtGdiCreateCompatibleDC failed to create hdc.\n");
1367 return 0;
1368 }
1369
1371 abs(pbmiSafe->bmiHeader.biWidth),
1372 abs(pbmiSafe->bmiHeader.biHeight));
1373 if (hBitmap == NULL)
1374 {
1375 DPRINT1("NtGdiCreateCompatibleBitmap failed to create bitmap.\n");
1376 DPRINT1("hdc : 0x%08x \n", hdc);
1377 DPRINT1("width : 0x%08x \n", pbmiSafe->bmiHeader.biWidth);
1378 DPRINT1("height : 0x%08x \n", pbmiSafe->bmiHeader.biHeight);
1380 return 0;
1381 }
1382
1383 /* Select the bitmap into hdcMem, and save a handle to the old bitmap */
1384 hOldBitmap = NtGdiSelectBitmap(hdcMem, hBitmap);
1385
1386 if (dwUsage == DIB_PAL_COLORS)
1387 {
1389 hPal = GdiSelectPalette(hdcMem, hPal, FALSE);
1390 }
1391
1392 pdc = DC_LockDc(hdcMem);
1393 if (pdc != NULL)
1394 {
1395 IntSetDIBits(pdc, hBitmap, 0, abs(pbmiSafe->bmiHeader.biHeight), pvBits,
1396 cjMaxBits, pbmiSafe, dwUsage);
1397 DC_UnlockDc(pdc);
1398 }
1399
1400 /* Origin for DIBitmap may be bottom left (positive biHeight) or top
1401 left (negative biHeight) */
1402 if (cxSrc == cxDst && cySrc == cyDst)
1403 {
1404 NtGdiBitBlt(hdc, xDst, yDst, cxDst, cyDst,
1405 hdcMem, xSrc, abs(pbmiSafe->bmiHeader.biHeight) - cySrc - ySrc,
1406 dwRop, 0, 0);
1407 }
1408 else
1409 {
1410 NtGdiStretchBlt(hdc, xDst, yDst, cxDst, cyDst,
1411 hdcMem, xSrc, abs(pbmiSafe->bmiHeader.biHeight) - cySrc - ySrc,
1412 cxSrc, cySrc, dwRop, 0);
1413 }
1414
1415 /* cleanup */
1416 if (hPal)
1418
1419 if (hOldBitmap)
1420 NtGdiSelectBitmap(hdcMem, hOldBitmap);
1421
1424
1425 } /* End of dwRop == SRCCOPY */
1426 else
1427 { /* Start of dwRop != SRCCOPY */
1428 /* FIXME: Locking twice is cheesy, coord tranlation in UM will fix it */
1429 if (!(pdc = DC_LockDc(hdc)))
1430 {
1431 DPRINT1("Could not lock dc\n");
1433 goto cleanup;
1434 }
1435
1436 /* Calculate source and destination rect */
1437 rcSrc.left = xSrc;
1438 rcSrc.top = ySrc;
1439 rcSrc.right = xSrc + abs(cxSrc);
1440 rcSrc.bottom = ySrc + abs(cySrc);
1441 rcDst.left = xDst;
1442 rcDst.top = yDst;
1443 rcDst.right = rcDst.left + cxDst;
1444 rcDst.bottom = rcDst.top + cyDst;
1445 IntLPtoDP(pdc, (POINTL*)&rcDst, 2);
1446 RECTL_vOffsetRect(&rcDst, pdc->ptlDCOrig.x, pdc->ptlDCOrig.y);
1447
1448 if (pdc->fs & (DC_ACCUM_APP|DC_ACCUM_WMGR))
1449 {
1450 IntUpdateBoundsRect(pdc, &rcDst);
1451 }
1452
1453 BmpFormat = BitmapFormat(pbmiSafe->bmiHeader.biBitCount,
1454 pbmiSafe->bmiHeader.biCompression);
1455
1456 hbmTmp = GreCreateBitmapEx(pbmiSafe->bmiHeader.biWidth,
1457 abs(pbmiSafe->bmiHeader.biHeight),
1458 0,
1459 BmpFormat,
1460 pbmiSafe->bmiHeader.biHeight < 0 ? BMF_TOPDOWN : 0,
1461 cjMaxBits,
1462 pvBits,
1463 0);
1464
1465 if (!hbmTmp)
1466 {
1467 goto cleanup;
1468 }
1469
1470 psurfTmp = SURFACE_ShareLockSurface(hbmTmp);
1471 if (!psurfTmp)
1472 {
1473 goto cleanup;
1474 }
1475
1476 /* Create a palette for the DIB */
1477 ppalDIB = CreateDIBPalette(pbmiSafe, pdc, dwUsage);
1478 if (!ppalDIB)
1479 {
1480 goto cleanup;
1481 }
1482
1483 /* Prepare DC for blit */
1484 DC_vPrepareDCsForBlit(pdc, &rcDst, NULL, NULL);
1485
1486 psurfDst = pdc->dclevel.pSurface;
1487
1488 /* Initialize XLATEOBJ */
1490 ppalDIB,
1491 psurfDst->ppal,
1492 RGB(0xff, 0xff, 0xff),
1493 pdc->pdcattr->crBackgroundClr,
1494 pdc->pdcattr->crForegroundClr);
1495
1496 /* Perform the stretch operation */
1497 IntEngStretchBlt(&psurfDst->SurfObj,
1498 &psurfTmp->SurfObj,
1499 NULL,
1500 (CLIPOBJ *)&pdc->co,
1501 &exlo.xlo,
1502 &pdc->dclevel.ca,
1503 &rcDst,
1504 &rcSrc,
1505 NULL,
1506 &pdc->eboFill.BrushObject,
1507 NULL,
1508 WIN32_ROP3_TO_ENG_ROP4(dwRop));
1509
1510 /* Cleanup */
1511 DC_vFinishBlit(pdc, NULL);
1512 EXLATEOBJ_vCleanup(&exlo);
1513
1514 cleanup:
1515 if (ppalDIB) PALETTE_ShareUnlockPalette(ppalDIB);
1516 if (psurfTmp) SURFACE_ShareUnlockSurface(psurfTmp);
1517 if (hbmTmp) GreDeleteObject(hbmTmp);
1518 if (pdc) DC_UnlockDc(pdc);
1519 }
1520
1521 if (pvBits) ExFreePoolWithTag(pvBits, TAG_DIB);
1522
1523 /* This is not what MSDN says is returned from this function, but it
1524 * follows Wine's dlls/gdi32/dib.c function nulldrv_StretchDIBits
1525 * and it fixes over 100 gdi32:dib regression tests. */
1526 if (dwRop == SRCCOPY)
1527 {
1528 LinesCopied = abs(pbmiSafe->bmiHeader.biHeight);
1529 }
1530 else
1531 {
1532 LinesCopied = pbmiSafe->bmiHeader.biHeight;
1533 }
1534
1535 ExFreePoolWithTag(pbmiSafe, 'imBG');
1536
1537 return LinesCopied;
1538}
1539
1540
1541HBITMAP
1544 PDC Dc,
1545 INT width,
1546 INT height,
1547 UINT planes,
1548 UINT bpp,
1550 DWORD init,
1551 LPBYTE bits,
1554 DWORD coloruse)
1555{
1557 BOOL fColor;
1558 ULONG BmpFormat = 0;
1559
1560 if (planes && bpp)
1561 BmpFormat = BitmapFormat(planes * bpp, compression);
1562
1563 // Check if we should create a monochrome or color bitmap. We create a monochrome bitmap only if it has exactly 2
1564 // colors, which are black followed by white, nothing else. In all other cases, we create a color bitmap.
1565
1566 if (BmpFormat != BMF_1BPP) fColor = TRUE;
1567 else if ((coloruse > DIB_RGB_COLORS) || ((init & CBM_INIT) == 0) || !data) fColor = FALSE;
1568 else
1569 {
1570 const RGBQUAD *rgb = (RGBQUAD*)((PBYTE)data + data->bmiHeader.biSize);
1571 DWORD col = RGB(rgb->rgbRed, rgb->rgbGreen, rgb->rgbBlue);
1572
1573 // Check if the first color of the colormap is black
1574 if (col == RGB(0, 0, 0))
1575 {
1576 rgb++;
1577 col = RGB(rgb->rgbRed, rgb->rgbGreen, rgb->rgbBlue);
1578
1579 // If the second color is white, create a monochrome bitmap
1580 fColor = (col != RGB(0xff,0xff,0xff));
1581 }
1582 else fColor = TRUE;
1583 }
1584
1585 // Now create the bitmap
1586 if (fColor)
1587 {
1588 if (init & CBM_CREATDIB)
1589 {
1590 PSURFACE Surface;
1591 PPALETTE Palette;
1592
1593 /* Undocumented flag which creates a DDB of the format specified by the bitmap info. */
1595 if (!handle)
1596 {
1597 DPRINT1("IntCreateCompatibleBitmap() failed!\n");
1598 return NULL;
1599 }
1600
1601 /* The palette must also match the given data */
1603 ASSERT(Surface);
1604 Palette = CreateDIBPalette(data, Dc, coloruse);
1605 if (Palette == NULL)
1606 {
1609 return NULL;
1610 }
1611
1612 SURFACE_vSetPalette(Surface, Palette);
1613
1616 }
1617 else
1618 {
1619 /* Create a regular compatible bitmap, in the same format as the device */
1621 }
1622 }
1623 else
1624 {
1626 abs(height),
1627 1,
1628 1,
1629 NULL);
1630 }
1631
1632 if (height < 0)
1633 height = -height;
1634
1635 if ((NULL != handle) && (CBM_INIT & init))
1636 {
1637 IntSetDIBits(Dc, handle, 0, height, bits, cjMaxBits, data, coloruse);
1638 }
1639
1640 return handle;
1641}
1642
1643// The CreateDIBitmap function creates a device-dependent bitmap (DDB) from a DIB and, optionally, sets the bitmap bits
1644// The DDB that is created will be whatever bit depth your reference DC is
1645HBITMAP
1648 IN HDC hDc,
1649 IN INT cx,
1650 IN INT cy,
1651 IN DWORD fInit,
1652 IN OPTIONAL LPBYTE pjInit,
1654 IN DWORD iUsage,
1655 IN UINT cjMaxInitInfo,
1657 IN FLONG fl,
1659{
1661 PBYTE safeBits = NULL;
1662 HBITMAP hbmResult = NULL;
1663
1664 if (pjInit == NULL)
1665 {
1666 fInit &= ~CBM_INIT;
1667 }
1668
1669 if(pjInit && (fInit & CBM_INIT))
1670 {
1671 if (cjMaxBits == 0) return NULL;
1673 if(!safeBits)
1674 {
1675 DPRINT1("Failed to allocate %lu bytes\n", cjMaxBits);
1677 return NULL;
1678 }
1679 }
1680
1681 _SEH2_TRY
1682 {
1683 if(pbmi) ProbeForRead(pbmi, cjMaxInitInfo, 1);
1684 if(pjInit && (fInit & CBM_INIT))
1685 {
1686 ProbeForRead(pjInit, cjMaxBits, 1);
1687 RtlCopyMemory(safeBits, pjInit, cjMaxBits);
1688 }
1689 }
1691 {
1693 }
1694 _SEH2_END;
1695
1696 if(!NT_SUCCESS(Status))
1697 {
1698 DPRINT1("Got an exception! pjInit = %p\n", pjInit);
1700 goto cleanup;
1701 }
1702
1703 hbmResult = GreCreateDIBitmapInternal(hDc,
1704 cx,
1705 cy,
1706 fInit,
1707 safeBits,
1708 pbmi,
1709 iUsage,
1710 fl,
1711 cjMaxBits,
1712 hcmXform);
1713
1714cleanup:
1715 if (safeBits) ExFreePoolWithTag(safeBits, TAG_DIB);
1716 return hbmResult;
1717}
1718
1719HBITMAP
1720NTAPI
1722 IN HDC hDc,
1723 IN INT cx,
1724 IN INT cy,
1725 IN DWORD fInit,
1726 IN OPTIONAL LPBYTE pjInit,
1728 IN DWORD iUsage,
1729 IN FLONG fl,
1732{
1733 PDC Dc;
1734 HBITMAP Bmp;
1735 USHORT bpp, planes;
1737 HDC hdcDest;
1738
1739 if (!hDc) /* 1bpp monochrome bitmap */
1740 {
1741 // Should use System Bitmap DC hSystemBM, with CreateCompatibleDC for this.
1742 hdcDest = NtGdiCreateCompatibleDC(0);
1743 if(!hdcDest)
1744 {
1745 DPRINT1("NtGdiCreateCompatibleDC failed\n");
1746 return NULL;
1747 }
1748 }
1749 else
1750 {
1751 hdcDest = hDc;
1752 }
1753
1754 Dc = DC_LockDc(hdcDest);
1755 if (!Dc)
1756 {
1757 DPRINT1("Failed to lock hdcDest %p\n", hdcDest);
1759 return NULL;
1760 }
1761 /* It's OK to set bpp=0 here, as IntCreateDIBitmap will create a compatible Bitmap
1762 * if bpp != 1 and ignore the real value that was passed */
1763 if (pbmi)
1764 {
1765 if (pbmi->bmiHeader.biSize == sizeof(BITMAPCOREHEADER))
1766 {
1768 bpp = CoreHeader->bcBitCount;
1769 planes = CoreHeader->bcPlanes ? CoreHeader->bcPlanes : 1;
1771 }
1772 else
1773 {
1775 planes = pbmi->bmiHeader.biPlanes ? pbmi->bmiHeader.biPlanes : 1;
1777 }
1778 }
1779 else
1780 {
1781 bpp = 0;
1782 planes = 0;
1783 compression = 0;
1784 }
1785 Bmp = IntCreateDIBitmap(Dc, cx, cy, planes, bpp, compression, fInit, pjInit, cjMaxBits, pbmi, iUsage);
1786 DC_UnlockDc(Dc);
1787
1788 if(!hDc)
1789 {
1790 NtGdiDeleteObjectApp(hdcDest);
1791 }
1792 return Bmp;
1793}
1794
1795HBITMAP
1796NTAPI
1798 _In_reads_(cjPackedDIB )PVOID pvPackedDIB,
1799 _In_ UINT cjPackedDIB,
1800 _In_ ULONG uUsage)
1801{
1803 PBYTE pjBits;
1804 UINT cjInfo, cjBits;
1805 HBITMAP hbm;
1806
1807 /* We only support BITMAPINFOHEADER, make sure the size is ok */
1808 if (cjPackedDIB < sizeof(BITMAPINFOHEADER))
1809 {
1810 return NULL;
1811 }
1812
1813 /* The packed DIB starts with the BITMAPINFOHEADER */
1814 pbmi = pvPackedDIB;
1815
1816 if (cjPackedDIB < pbmi->bmiHeader.biSize)
1817 {
1818 return NULL;
1819 }
1820
1821 /* Calculate the info size and make sure the packed DIB is large enough */
1822 cjInfo = DIB_BitmapInfoSize(pbmi, uUsage);
1823 if (cjPackedDIB <= cjInfo)
1824 {
1825 return NULL;
1826 }
1827
1828 /* The bitmap bits start after the header */
1829 pjBits = (PBYTE)pvPackedDIB + cjInfo;
1830 cjBits = cjPackedDIB - cjInfo;
1831
1836 pjBits,
1837 pbmi,
1838 uUsage,
1839 0,
1840 cjBits,
1841 NULL);
1842
1843 return hbm;
1844}
1845
1846HBITMAP
1849 IN HDC hDC,
1852 IN BITMAPINFO* bmi,
1853 IN DWORD Usage,
1854 IN UINT cjHeader,
1855 IN FLONG fl,
1856 IN ULONG_PTR dwColorSpace,
1857 OUT PVOID *Bits)
1858{
1859 HBITMAP hbitmap = 0;
1860 DC *dc;
1861 BOOL bDesktopDC = FALSE;
1863
1864 if (!bmi) return hbitmap; // Make sure.
1865
1866 _SEH2_TRY
1867 {
1868 ProbeForRead(&bmi->bmiHeader.biSize, sizeof(DWORD), 1);
1869 ProbeForRead(bmi, bmi->bmiHeader.biSize, 1);
1870 ProbeForRead(bmi, DIB_BitmapInfoSize(bmi, (WORD)Usage), 1);
1871 }
1873 {
1875 }
1876 _SEH2_END;
1877
1878 if(!NT_SUCCESS(Status))
1879 {
1881 return NULL;
1882 }
1883
1884 // If the reference hdc is null, take the desktop dc
1885 if (hDC == 0)
1886 {
1888 bDesktopDC = TRUE;
1889 }
1890
1891 if ((dc = DC_LockDc(hDC)))
1892 {
1894 bmi,
1895 Usage,
1896 Bits,
1897 hSection,
1898 dwOffset,
1899 0);
1900 DC_UnlockDc(dc);
1901 }
1902 else
1903 {
1905 }
1906
1907 if (bDesktopDC)
1909
1910 return hbitmap;
1911}
1912
1913HBITMAP
1916 PDC dc,
1917 CONST BITMAPINFO *bmi,
1918 UINT usage,
1919 LPVOID *bits,
1921 DWORD offset,
1922 DWORD ovr_pitch)
1923{
1924 HBITMAP res = 0;
1925 SURFACE *bmp = NULL;
1926 void *mapBits = NULL;
1927 PPALETTE ppalDIB = NULL;
1928
1929 // Fill BITMAP32 structure with DIB data
1930 CONST BITMAPINFOHEADER *bi = &bmi->bmiHeader;
1931 INT effHeight;
1932 ULONG totalSize;
1933 BITMAP bm;
1934 //SIZEL Size;
1935 HANDLE hSecure;
1936
1937 DPRINT("format (%ld,%ld), planes %u, bpp %u, size %lu, colors %lu (%s)\n",
1938 bi->biWidth, bi->biHeight, bi->biPlanes, bi->biBitCount,
1939 bi->biSizeImage, bi->biClrUsed, usage == DIB_PAL_COLORS? "PAL" : "RGB");
1940
1941 /* CreateDIBSection should fail for compressed formats */
1942 if (bi->biCompression == BI_RLE4 || bi->biCompression == BI_RLE8)
1943 {
1944 DPRINT1("no compressed format allowed\n");
1945 return (HBITMAP)NULL;
1946 }
1947
1948 effHeight = bi->biHeight >= 0 ? bi->biHeight : -bi->biHeight;
1949 bm.bmType = 0;
1950 bm.bmWidth = bi->biWidth;
1951 bm.bmHeight = effHeight;
1952 bm.bmWidthBytes = ovr_pitch ? ovr_pitch : WIDTH_BYTES_ALIGN32(bm.bmWidth, bi->biBitCount);
1953
1954 bm.bmPlanes = bi->biPlanes;
1955 bm.bmBitsPixel = bi->biBitCount;
1956 bm.bmBits = NULL;
1957
1958 // Get storage location for DIB bits. Only use biSizeImage if it's valid and
1959 // we're dealing with a compressed bitmap. Otherwise, use width * height.
1960 totalSize = (bi->biSizeImage && (bi->biCompression != BI_RGB) && (bi->biCompression != BI_BITFIELDS))
1961 ? bi->biSizeImage : (ULONG)(bm.bmWidthBytes * effHeight);
1962
1963 if (section)
1964 {
1967 DWORD mapOffset;
1969 SIZE_T mapSize;
1970
1972 &Sbi,
1973 sizeof Sbi,
1974 0);
1975 if (!NT_SUCCESS(Status))
1976 {
1977 DPRINT1("ZwQuerySystemInformation failed (0x%lx)\n", Status);
1978 return NULL;
1979 }
1980
1981 mapOffset = offset - (offset % Sbi.AllocationGranularity);
1982 mapSize = totalSize + (offset - mapOffset);
1983
1984 SectionOffset.LowPart = mapOffset;
1985 SectionOffset.HighPart = 0;
1986
1987 Status = ZwMapViewOfSection(section,
1989 &mapBits,
1990 0,
1991 0,
1993 &mapSize,
1994 ViewShare,
1995 0,
1997 if (!NT_SUCCESS(Status))
1998 {
1999 DPRINT1("ZwMapViewOfSection failed (0x%lx)\n", Status);
2001 return NULL;
2002 }
2003
2004 if (mapBits) bm.bmBits = (char *)mapBits + (offset - mapOffset);
2005 }
2006 else if (ovr_pitch && offset)
2007 bm.bmBits = UlongToPtr(offset);
2008 else
2009 {
2010 offset = 0;
2011 bm.bmBits = EngAllocUserMem(totalSize, 0);
2012 if(!bm.bmBits)
2013 {
2014 DPRINT1("Failed to allocate memory\n");
2015 goto cleanup;
2016 }
2017 }
2018
2019// hSecure = MmSecureVirtualMemory(bm.bmBits, totalSize, PAGE_READWRITE);
2020 hSecure = (HANDLE)0x1; // HACK OF UNIMPLEMENTED KERNEL STUFF !!!!
2021
2022
2023 // Create Device Dependent Bitmap and add DIB pointer
2024 //Size.cx = bm.bmWidth;
2025 //Size.cy = abs(bm.bmHeight);
2026 res = GreCreateBitmapEx(bm.bmWidth,
2027 abs(bm.bmHeight),
2028 bm.bmWidthBytes,
2029 BitmapFormat(bi->biBitCount * bi->biPlanes, bi->biCompression),
2031 ((bi->biHeight < 0) ? BMF_TOPDOWN : 0),
2032 totalSize,
2033 bm.bmBits,
2034 0);
2035 if (!res)
2036 {
2037 DPRINT1("GreCreateBitmapEx failed\n");
2039 goto cleanup;
2040 }
2041 bmp = SURFACE_ShareLockSurface(res); // HACK
2042 if (NULL == bmp)
2043 {
2044 DPRINT1("SURFACE_LockSurface failed\n");
2046 goto cleanup;
2047 }
2048
2049 /* WINE NOTE: WINE makes use of a colormap, which is a color translation
2050 table between the DIB and the X physical device. Obviously,
2051 this is left out of the ReactOS implementation. Instead,
2052 we call NtGdiSetDIBColorTable. */
2053 bmp->hDIBSection = section;
2054 bmp->hSecure = hSecure;
2055 bmp->dwOffset = offset;
2056 bmp->flags = API_BITMAP;
2057 bmp->biClrImportant = bi->biClrImportant;
2058
2059 /* Create a palette for the DIB */
2060 ppalDIB = CreateDIBPalette(bmi, dc, usage);
2061
2062 // Clean up in case of errors
2063cleanup:
2064 if (!res || !bmp || !bm.bmBits || !ppalDIB)
2065 {
2066 DPRINT("Got an error res=%p, bmp=%p, bm.bmBits=%p\n", res, bmp, bm.bmBits);
2067 if (bm.bmBits)
2068 {
2069 // MmUnsecureVirtualMemory(hSecure); // FIXME: Implement this!
2070 if (section)
2071 {
2072 ZwUnmapViewOfSection(NtCurrentProcess(), mapBits);
2073 bm.bmBits = NULL;
2074 }
2075 else if (!offset)
2076 EngFreeUserMem(bm.bmBits), bm.bmBits = NULL;
2077 }
2078
2079 if (bmp)
2080 {
2082 bmp = NULL;
2083 }
2084
2085 if (res)
2086 {
2088 res = 0;
2089 }
2090
2091 if(ppalDIB)
2092 {
2094 }
2095 }
2096
2097 if (bmp)
2098 {
2099 /* If we're here, everything went fine */
2100 SURFACE_vSetPalette(bmp, ppalDIB);
2103 }
2104
2105 // Return BITMAP handle and storage location
2106 if (NULL != bm.bmBits && NULL != bits)
2107 {
2108 *bits = bm.bmBits;
2109 }
2110
2111 return res;
2112}
2113
2114/***********************************************************************
2115 * DIB_GetBitmapInfo
2116 *
2117 * Get the info from a bitmap header.
2118 * Return 0 for COREHEADER, 1 for INFOHEADER, -1 for error.
2119 */
2120int
2123 LONG *height, WORD *planes, WORD *bpp, DWORD *compr, DWORD *size )
2124{
2125 if (header->biSize == sizeof(BITMAPCOREHEADER))
2126 {
2127 const BITMAPCOREHEADER *core = (const BITMAPCOREHEADER *)header;
2128 *width = core->bcWidth;
2129 *height = core->bcHeight;
2130 *planes = core->bcPlanes;
2131 *bpp = core->bcBitCount;
2132 *compr = BI_RGB;
2133 *size = 0;
2134 return 0;
2135 }
2136 if (header->biSize >= sizeof(BITMAPINFOHEADER)) /* Assume BITMAPINFOHEADER */
2137 {
2138 *width = header->biWidth;
2139 *height = header->biHeight;
2140 *planes = header->biPlanes;
2141 *bpp = header->biBitCount;
2142 *compr = header->biCompression;
2143 *size = header->biSizeImage;
2144 return 1;
2145 }
2146 DPRINT1("(%u): unknown/wrong size for header\n", header->biSize );
2147 return -1;
2148}
2149
2150/***********************************************************************
2151 * DIB_GetDIBImageBytes
2152 *
2153 * Return the number of bytes used to hold the image in a DIB bitmap.
2154 * 11/16/1999 (RJJ) lifted from wine
2155 */
2156
2158{
2159 return WIDTH_BYTES_ALIGN32(width, depth) * (height < 0 ? -height : height);
2160}
2161
2162/***********************************************************************
2163 * DIB_BitmapInfoSize
2164 *
2165 * Return the size of the bitmap info structure including color table.
2166 * 11/16/1999 (RJJ) lifted from wine
2167 */
2168
2170{
2171 unsigned int colors, size, masks = 0;
2172 unsigned int colorsize;
2173
2174 colorsize = (coloruse == DIB_RGB_COLORS) ? sizeof(RGBQUAD) :
2175 (coloruse == DIB_PAL_INDICES) ? 0 :
2176 sizeof(WORD);
2177
2178 if (info->bmiHeader.biSize == sizeof(BITMAPCOREHEADER))
2179 {
2180 const BITMAPCOREHEADER *core = (const BITMAPCOREHEADER *)info;
2181 colors = (core->bcBitCount <= 8) ? 1 << core->bcBitCount : 0;
2182 return sizeof(BITMAPCOREHEADER) + colors * colorsize;
2183 }
2184 else /* Assume BITMAPINFOHEADER */
2185 {
2186 colors = info->bmiHeader.biClrUsed;
2187 if (colors > 256) colors = 256;
2188 if (!colors && (info->bmiHeader.biBitCount <= 8))
2189 colors = 1 << info->bmiHeader.biBitCount;
2190 if (info->bmiHeader.biCompression == BI_BITFIELDS) masks = 3;
2191 size = max( info->bmiHeader.biSize, sizeof(BITMAPINFOHEADER) + masks * sizeof(DWORD) );
2192 return size + colors * colorsize;
2193 }
2194}
2195
2196HPALETTE
2199{
2200 PPALETTE ppalNew;
2201 ULONG nNumColors,i;
2202 USHORT *lpIndex;
2203 HPALETTE hpal;
2204
2205 if (!(ppalDc->flFlags & PAL_INDEXED))
2206 {
2207 return NULL;
2208 }
2209
2210 nNumColors = 1 << lpbmi->bmiHeader.biBitCount;
2211 if (lpbmi->bmiHeader.biClrUsed)
2212 {
2213 nNumColors = min(nNumColors, lpbmi->bmiHeader.biClrUsed);
2214 }
2215
2216 ppalNew = PALETTE_AllocPalWithHandle(PAL_INDEXED, nNumColors, NULL, 0, 0, 0);
2217 if (ppalNew == NULL)
2218 {
2219 DPRINT1("Could not allocate palette\n");
2220 return NULL;
2221 }
2222
2223 lpIndex = (USHORT *)((PBYTE)lpbmi + lpbmi->bmiHeader.biSize);
2224
2225 for (i = 0; i < nNumColors; i++)
2226 {
2227 ULONG iColorIndex = *lpIndex % ppalDc->NumColors;
2228 ppalNew->IndexedColors[i] = ppalDc->IndexedColors[iColorIndex];
2229 lpIndex++;
2230 }
2231
2232 hpal = ppalNew->BaseObject.hHmgr;
2233 PALETTE_UnlockPalette(ppalNew);
2234
2235 return hpal;
2236}
2237
2238/* Converts a BITMAPCOREINFO to a BITMAPINFO structure,
2239 * or does nothing if it's already a BITMAPINFO (or V4 or V5) */
2243{
2245 BITMAPINFO* pNewBmi ;
2246 UINT numColors = 0, ColorsSize = 0;
2247
2248 if(pbmi->bmiHeader.biSize >= sizeof(BITMAPINFOHEADER)) return (BITMAPINFO*)pbmi;
2249 if(pbmi->bmiHeader.biSize != sizeof(BITMAPCOREHEADER)) return NULL;
2250
2251 if(pbmci->bmciHeader.bcBitCount <= 8)
2252 {
2253 numColors = 1 << pbmci->bmciHeader.bcBitCount;
2254 if(Usage == DIB_PAL_COLORS)
2255 {
2256 ColorsSize = numColors * sizeof(WORD);
2257 }
2258 else
2259 {
2260 ColorsSize = numColors * sizeof(RGBQUAD);
2261 }
2262 }
2263 else if (Usage == DIB_PAL_COLORS)
2264 {
2265 /* Invalid at high-res */
2266 return NULL;
2267 }
2268
2269 pNewBmi = ExAllocatePoolWithTag(PagedPool, sizeof(BITMAPINFOHEADER) + ColorsSize, TAG_DIB);
2270 if(!pNewBmi) return NULL;
2271
2272 RtlZeroMemory(pNewBmi, sizeof(BITMAPINFOHEADER) + ColorsSize);
2273
2274 pNewBmi->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
2275 pNewBmi->bmiHeader.biBitCount = pbmci->bmciHeader.bcBitCount;
2276 pNewBmi->bmiHeader.biWidth = pbmci->bmciHeader.bcWidth;
2277 pNewBmi->bmiHeader.biHeight = pbmci->bmciHeader.bcHeight;
2278 pNewBmi->bmiHeader.biPlanes = pbmci->bmciHeader.bcPlanes;
2279 pNewBmi->bmiHeader.biCompression = BI_RGB ;
2281 pNewBmi->bmiHeader.biHeight,
2282 pNewBmi->bmiHeader.biBitCount);
2283 pNewBmi->bmiHeader.biClrUsed = numColors;
2284
2285 if(Usage == DIB_PAL_COLORS)
2286 {
2287 RtlCopyMemory(pNewBmi->bmiColors, pbmci->bmciColors, ColorsSize);
2288 }
2289 else
2290 {
2291 UINT i;
2292 for(i=0; i<numColors; i++)
2293 {
2294 pNewBmi->bmiColors[i].rgbRed = pbmci->bmciColors[i].rgbtRed;
2295 pNewBmi->bmiColors[i].rgbGreen = pbmci->bmciColors[i].rgbtGreen;
2296 pNewBmi->bmiColors[i].rgbBlue = pbmci->bmciColors[i].rgbtBlue;
2297 }
2298 }
2299
2300 return pNewBmi ;
2301}
2302
2303/* Frees a BITMAPINFO created with DIB_ConvertBitmapInfo */
2304VOID
2307{
2308 BITMAPCOREINFO* pbmci;
2309 if(converted == orig)
2310 return;
2311
2312 if(usage == -1)
2313 {
2314 /* Caller don't want any conversion */
2315 ExFreePoolWithTag(converted, TAG_DIB);
2316 return;
2317 }
2318
2319 /* Perform inverse conversion */
2320 pbmci = (BITMAPCOREINFO*)orig;
2321
2322 ASSERT(pbmci->bmciHeader.bcSize == sizeof(BITMAPCOREHEADER));
2323 pbmci->bmciHeader.bcBitCount = converted->bmiHeader.biBitCount;
2324 pbmci->bmciHeader.bcWidth = converted->bmiHeader.biWidth;
2325 pbmci->bmciHeader.bcHeight = converted->bmiHeader.biHeight;
2326 pbmci->bmciHeader.bcPlanes = converted->bmiHeader.biPlanes;
2327
2328 if(pbmci->bmciHeader.bcBitCount <= 8)
2329 {
2330 UINT numColors = converted->bmiHeader.biClrUsed;
2331 if(!numColors) numColors = 1 << pbmci->bmciHeader.bcBitCount;
2332 if(usage == DIB_PAL_COLORS)
2333 {
2334 RtlZeroMemory(pbmci->bmciColors, (1 << pbmci->bmciHeader.bcBitCount) * sizeof(WORD));
2335 RtlCopyMemory(pbmci->bmciColors, converted->bmiColors, numColors * sizeof(WORD));
2336 }
2337 else
2338 {
2339 UINT i;
2340 RtlZeroMemory(pbmci->bmciColors, (1 << pbmci->bmciHeader.bcBitCount) * sizeof(RGBTRIPLE));
2341 for(i=0; i<numColors; i++)
2342 {
2343 pbmci->bmciColors[i].rgbtRed = converted->bmiColors[i].rgbRed;
2344 pbmci->bmciColors[i].rgbtGreen = converted->bmiColors[i].rgbGreen;
2345 pbmci->bmciColors[i].rgbtBlue = converted->bmiColors[i].rgbBlue;
2346 }
2347 }
2348 }
2349 /* Now free it, it's not needed anymore */
2350 ExFreePoolWithTag(converted, TAG_DIB);
2351}
2352
2353/* EOF */
static HDC hDC
Definition: 3dtext.c:33
#define DIB_PAL_INDICES
#define CBM_CREATDIB
static HBITMAP hbitmap
#define VOID
Definition: acefi.h:82
LONG NTSTATUS
Definition: precomp.h:26
#define DPRINT1
Definition: precomp.h:8
#define R3_OPINDEX_SRCCOPY
Definition: bitblt.h:27
BOOL APIENTRY IntEngCopyBits(SURFOBJ *psoTrg, SURFOBJ *psoSrc, CLIPOBJ *pco, XLATEOBJ *pxlo, RECTL *prclTrg, POINTL *pptlSrc)
Definition: bitblt_new.c:678
HBITMAP FASTCALL IntCreateCompatibleBitmap(PDC Dc, INT Width, INT Height, UINT Planes, UINT Bpp)
Definition: bitmaps.c:273
HBITMAP NTAPI GreCreateBitmapEx(_In_ ULONG nWidth, _In_ ULONG nHeight, _In_ ULONG cjWidthBytes, _In_ ULONG iFormat, _In_ USHORT fjBitmap, _In_ ULONG cjSizeImage, _In_opt_ PVOID pvBits, _In_ FLONG flags)
Definition: bitmaps.c:101
HBITMAP NTAPI GreCreateBitmap(_In_ ULONG nWidth, _In_ ULONG nHeight, _In_ ULONG cPlanes, _In_ ULONG cBitsPixel, _In_opt_ PVOID pvBits)
Definition: bitmaps.c:172
_In_ fcb _In_ chunk _In_ uint64_t _In_ uint64_t _In_ bool _In_opt_ void _In_opt_ PIRP _In_ LIST_ENTRY _In_ uint8_t compression
Definition: btrfs_drv.h:1365
HGDIOBJ hHmgr(VOID)
Definition: baseobj.hpp:95
static BOOLEAN IntLPtoDP(DC *pdc, PPOINTL ppt, UINT count)
Definition: coord.h:182
VOID FASTCALL DC_vPrepareDCsForBlit(PDC pdcDest, const RECT *rcDest, PDC pdcSrc, const RECT *rcSrc)
Definition: dclife.c:505
VOID FASTCALL DC_vFinishBlit(PDC pdc1, PDC pdc2)
Definition: dclife.c:614
FORCEINLINE VOID DC_UnlockDc(PDC pdc)
Definition: dc.h:238
VOID FASTCALL IntUpdateBoundsRect(PDC, PRECTL)
Definition: dcutil.c:694
HPALETTE NTAPI GdiSelectPalette(_In_ HDC hDC, _In_ HPALETTE hpal, _In_ BOOL ForceBackground)
@ DCTYPE_INFO
Definition: dc.h:43
@ DC_ACCUM_APP
Definition: dc.h:25
@ DC_ACCUM_WMGR
Definition: dc.h:24
FORCEINLINE PDC DC_LockDc(HDC hdc)
Definition: dc.h:220
#define ERROR_NOT_ENOUGH_MEMORY
Definition: dderror.h:7
HBITMAP NTAPI GreCreateDIBitmapFromPackedDIB(_In_reads_(cjPackedDIB) PVOID pvPackedDIB, _In_ UINT cjPackedDIB, _In_ ULONG uUsage)
Definition: dibobj.c:1797
static const RGBQUAD DefLogPaletteQuads[20]
Definition: dibobj.c:14
BITMAPINFO *FASTCALL DIB_ConvertBitmapInfo(CONST BITMAPINFO *pbmi, DWORD Usage)
Definition: dibobj.c:2242
int FASTCALL DIB_GetBitmapInfo(const BITMAPINFOHEADER *header, LONG *width, LONG *height, WORD *planes, WORD *bpp, DWORD *compr, DWORD *size)
Definition: dibobj.c:2122
VOID FASTCALL DIB_FreeConvertedBitmapInfo(BITMAPINFO *converted, BITMAPINFO *orig, DWORD usage)
Definition: dibobj.c:2306
static INT FASTCALL IntSetDIBits(PDC DC, HBITMAP hBitmap, UINT StartScan, UINT ScanLines, CONST VOID *Bits, ULONG cjMaxBits, CONST BITMAPINFO *bmi, UINT ColorUse)
Definition: dibobj.c:239
INT FASTCALL DIB_BitmapInfoSize(const BITMAPINFO *info, WORD coloruse)
Definition: dibobj.c:2169
W32KAPI INT APIENTRY NtGdiSetDIBitsToDeviceInternal(IN HDC hDC, IN INT XDest, IN INT YDest, IN DWORD Width, IN DWORD Height, IN INT XSrc, IN INT YSrc, IN DWORD StartScan, IN DWORD ScanLines, IN LPBYTE Bits, IN LPBITMAPINFO bmi, IN DWORD ColorUse, IN UINT cjMaxBits, IN UINT cjMaxInfo, IN BOOL bTransformCoordinates, IN OPTIONAL HANDLE hcmXform)
Definition: dibobj.c:470
HBITMAP NTAPI GreCreateDIBitmapInternal(IN HDC hDc, IN INT cx, IN INT cy, IN DWORD fInit, IN OPTIONAL LPBYTE pjInit, IN OPTIONAL PBITMAPINFO pbmi, IN DWORD iUsage, IN FLONG fl, IN UINT cjMaxBits, IN HANDLE hcmXform)
Definition: dibobj.c:1721
HBITMAP APIENTRY NtGdiCreateDIBSection(IN HDC hDC, IN OPTIONAL HANDLE hSection, IN DWORD dwOffset, IN BITMAPINFO *bmi, IN DWORD Usage, IN UINT cjHeader, IN FLONG fl, IN ULONG_PTR dwColorSpace, OUT PVOID *Bits)
Definition: dibobj.c:1848
HPALETTE FASTCALL DIB_MapPaletteColors(PPALETTE ppalDc, CONST BITMAPINFO *lpbmi)
Definition: dibobj.c:2198
static HBITMAP IntGdiCreateMaskFromRLE(DWORD Width, DWORD Height, ULONG Compression, const BYTE *Bits, DWORD BitsSize)
Definition: dibobj.c:360
INT APIENTRY DIB_GetDIBImageBytes(INT width, INT height, INT depth)
Definition: dibobj.c:2157
W32KAPI INT APIENTRY NtGdiStretchDIBitsInternal(IN HDC hdc, IN INT xDst, IN INT yDst, IN INT cxDst, IN INT cyDst, IN INT xSrc, IN INT ySrc, IN INT cxSrc, IN INT cySrc, IN OPTIONAL LPBYTE pjInit, IN LPBITMAPINFO pbmi, IN DWORD dwUsage, IN DWORD dwRop, IN UINT cjMaxInfo, IN UINT cjMaxBits, IN HANDLE hcmXform)
Definition: dibobj.c:1225
PPALETTE NTAPI CreateDIBPalette(_In_ const BITMAPINFO *pbmi, _In_ PDC pdc, _In_ ULONG iUsage)
Definition: dibobj.c:41
INT APIENTRY GreGetDIBitsInternal(HDC hDC, HBITMAP hBitmap, UINT StartScan, UINT ScanLines, LPBYTE Bits, LPBITMAPINFO Info, UINT Usage, UINT MaxBits, UINT MaxInfo)
Definition: dibobj.c:718
HBITMAP APIENTRY NtGdiCreateDIBitmapInternal(IN HDC hDc, IN INT cx, IN INT cy, IN DWORD fInit, IN OPTIONAL LPBYTE pjInit, IN OPTIONAL LPBITMAPINFO pbmi, IN DWORD iUsage, IN UINT cjMaxInitInfo, IN UINT cjMaxBits, IN FLONG fl, IN HANDLE hcmXform)
Definition: dibobj.c:1647
HBITMAP APIENTRY DIB_CreateDIBSection(PDC dc, CONST BITMAPINFO *bmi, UINT usage, LPVOID *bits, HANDLE section, DWORD offset, DWORD ovr_pitch)
Definition: dibobj.c:1915
HBITMAP FASTCALL IntCreateDIBitmap(PDC Dc, INT width, INT height, UINT planes, UINT bpp, ULONG compression, DWORD init, LPBYTE bits, ULONG cjMaxBits, PBITMAPINFO data, DWORD coloruse)
Definition: dibobj.c:1543
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
static HBITMAP hBitmap
Definition: timezone.c:26
DWORD bpp
Definition: surface.c:185
#define APIENTRY
Definition: api.h:79
#define ERROR_INVALID_PARAMETER
Definition: compat.h:101
#define ERROR_INVALID_HANDLE
Definition: compat.h:98
static void cleanup(void)
Definition: main.c:1335
#define BI_RLE4
Definition: precomp.h:48
#define BI_RGB
Definition: precomp.h:47
#define RGB(r, g, b)
Definition: precomp.h:62
ULONG RGBQUAD
Definition: precomp.h:50
#define UlongToPtr(u)
Definition: config.h:106
#define ExAllocatePoolWithTag(hernya, size, tag)
Definition: env_spec_w32.h:350
#define PagedPool
Definition: env_spec_w32.h:308
VOID NTAPI ProbeForRead(IN CONST VOID *Address, IN SIZE_T Length, IN ULONG Alignment)
Definition: exintrin.c:102
VOID NTAPI ProbeForWrite(IN PVOID Address, IN SIZE_T Length, IN ULONG Alignment)
Definition: exintrin.c:143
#define abs(i)
Definition: fconv.c:206
#define _SEH2_END
Definition: filesup.c:22
#define _SEH2_TRY
Definition: filesup.c:19
unsigned int BOOL
Definition: ntddk_ex.h:94
unsigned long DWORD
Definition: ntddk_ex.h:95
NTSYSAPI NTSTATUS NTAPI ZwQuerySystemInformation(IN SYSTEM_INFORMATION_CLASS SystemInfoClass, OUT PVOID SystemInfoBuffer, IN ULONG SystemInfoBufferSize, OUT PULONG BytesReturned OPTIONAL)
@ SystemBasicInformation
Definition: ntddk_ex.h:11
unsigned short WORD
Definition: ntddk_ex.h:93
unsigned int Mask
Definition: fpcontrol.c:82
#define GDI_OBJECT_TYPE_PALETTE
Definition: gdi.h:49
Status
Definition: gdiplustypes.h:25
GLint GLint GLsizei GLsizei GLsizei depth
Definition: gl.h:1546
GLint GLint GLint GLint GLint x
Definition: gl.h:1548
GLint GLint GLint GLint GLint GLint y
Definition: gl.h:1548
GLint GLenum GLsizei GLsizei GLsizei GLint GLsizei const GLvoid * data
Definition: gl.h:1950
GLint GLint GLsizei GLsizei height
Definition: gl.h:1546
GLint GLint GLsizei width
Definition: gl.h:1546
GLsizeiptr size
Definition: glext.h:5919
GLuint res
Definition: glext.h:9613
GLenum GLint GLenum GLsizei GLsizei GLsizei GLint GLsizei const GLvoid * bits
Definition: glext.h:10929
GLuint64EXT * result
Definition: glext.h:11304
GLsizeiptr const GLvoid GLenum usage
Definition: glext.h:5919
GLintptr offset
Definition: glext.h:5920
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
_Must_inspect_result_ _In_ USAGE _In_ USHORT _In_ USAGE Usage
Definition: hidpi.h:384
#define EXCEPTION_EXECUTE_HANDLER
Definition: excpt.h:85
#define ROP4_FROM_INDEX(index)
Definition: inteng.h:42
#define ROP4_MASK
Definition: inteng.h:55
BOOL APIENTRY IntEngStretchBlt(SURFOBJ *DestObj, SURFOBJ *SourceObj, SURFOBJ *Mask, CLIPOBJ *ClipRegion, XLATEOBJ *ColorTranslation, COLORADJUSTMENT *pca, RECTL *DestRect, RECTL *SourceRect, POINTL *pMaskOrigin, BRUSHOBJ *Brush, POINTL *BrushOrigin, ULONG Mode)
#define WIN32_ROP3_TO_ENG_ROP4(dwRop4)
Definition: intgdi.h:4
if(dx< 0)
Definition: linetemp.h:194
static const WCHAR dc[]
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
#define BI_BITFIELDS
Definition: mmreg.h:507
#define ASSERT(a)
Definition: mode.c:44
#define ExFreePoolWithTag(_P, _T)
Definition: module.h:1109
BITMAP bmp
Definition: alphablend.c:62
HDC hdc
Definition: main.c:9
static HBITMAP
Definition: button.c:44
static HDC
Definition: imagelist.c:92
static const BYTE masks[8]
Definition: dib.c:2760
#define min(a, b)
Definition: monoChain.cc:55
#define _Success_(expr)
Definition: ms_sal.h:259
#define _Inout_
Definition: ms_sal.h:378
#define _In_
Definition: ms_sal.h:308
#define _Out_writes_bytes_opt_(size)
Definition: ms_sal.h:351
#define _In_reads_(size)
Definition: ms_sal.h:319
unsigned int UINT
Definition: ndis.h:50
_In_ HANDLE _Outptr_result_bytebuffer_ ViewSize PVOID _In_ ULONG_PTR _In_ SIZE_T _Inout_opt_ PLARGE_INTEGER SectionOffset
Definition: mmfuncs.h:407
#define PAGE_READWRITE
Definition: nt_native.h:1304
#define FASTCALL
Definition: nt_native.h:50
#define NtCurrentProcess()
Definition: nt_native.h:1657
@ ViewShare
Definition: nt_native.h:1278
unsigned long FLONG
Definition: ntbasedef.h:366
_In_ HBITMAP hbm
Definition: ntgdi.h:2776
__kernel_entry W32KAPI HBITMAP APIENTRY NtGdiCreateCompatibleBitmap(_In_ HDC hdc, _In_ INT cx, _In_ INT cy)
_In_ HBITMAP _In_ UINT _In_ UINT _Inout_ LPBITMAPINFO _In_ UINT _In_ UINT _In_ UINT cjMaxInfo
Definition: ntgdi.h:2783
_In_ HBITMAP _In_ UINT _In_ UINT _Inout_ LPBITMAPINFO _In_ UINT _In_ UINT cjMaxBits
Definition: ntgdi.h:2782
__kernel_entry W32KAPI HDC APIENTRY NtGdiCreateCompatibleDC(_In_opt_ HDC hdc)
_In_ DWORD _In_ DWORD dwOffset
Definition: ntgdi.h:2033
__kernel_entry W32KAPI BOOL APIENTRY NtGdiBitBlt(_In_ HDC hdcDst, _In_ INT x, _In_ INT y, _In_ INT cx, _In_ INT cy, _In_opt_ HDC hdcSrc, _In_ INT xSrc, _In_ INT ySrc, _In_ DWORD rop4, _In_ DWORD crBackColor, _In_ FLONG fl)
#define W32KAPI
Definition: ntgdi.h:9
__kernel_entry W32KAPI BOOL APIENTRY NtGdiStretchBlt(_In_ HDC hdcDst, _In_ INT xDst, _In_ INT yDst, _In_ INT cxDst, _In_ INT cyDst, _In_opt_ HDC hdcSrc, _In_ INT xSrc, _In_ INT ySrc, _In_ INT cxSrc, _In_ INT cySrc, _In_ DWORD dwRop, _In_ DWORD dwBackColor)
_In_ HBITMAP _In_ UINT _In_ UINT cScans
Definition: ntgdi.h:2778
__kernel_entry W32KAPI HBITMAP APIENTRY NtGdiSelectBitmap(_In_ HDC hdc, _In_ HBITMAP hbm)
_In_ HBITMAP _In_ UINT _In_ UINT _Inout_ LPBITMAPINFO pbmi
Definition: ntgdi.h:2780
__kernel_entry W32KAPI HANDLE APIENTRY NtGdiGetDCObject(_In_ HDC hdc, _In_ INT itype)
__kernel_entry W32KAPI BOOL APIENTRY NtGdiDeleteObjectApp(_In_ HANDLE hobj)
_In_ HBITMAP _In_ UINT _In_ UINT _Inout_ LPBITMAPINFO _In_ UINT iUsage
Definition: ntgdi.h:2781
_In_ HBITMAP _In_ UINT iStartScan
Definition: ntgdi.h:2777
#define CONST
Definition: pedump.c:81
WORD * PWORD
Definition: pedump.c:67
BYTE * PBYTE
Definition: pedump.c:66
DWORD * PDWORD
Definition: pedump.c:68
long LONG
Definition: pedump.c:60
unsigned short USHORT
Definition: pedump.c:61
_Out_opt_ int _Out_opt_ int * cy
Definition: commctrl.h:586
_Out_opt_ int * cx
Definition: commctrl.h:585
#define _SEH2_GetExceptionCode()
Definition: pseh2_64.h:159
#define _SEH2_EXCEPT(...)
Definition: pseh2_64.h:34
#define STATUS_SUCCESS
Definition: shellext.h:65
#define DPRINT
Definition: sndvol32.h:71
static void Exit(void)
Definition: sock.c:1330
#define __kernel_entry
Definition: specstrings.h:355
PULONG MinorVersion OPTIONAL
Definition: CrossNt.h:68
DWORD bV4GreenMask
Definition: wingdi.h:1504
DWORD bV4RedMask
Definition: wingdi.h:1503
DWORD bV4BlueMask
Definition: wingdi.h:1505
Definition: polytest.cpp:41
long bottom
Definition: polytest.cpp:53
long right
Definition: polytest.cpp:53
long top
Definition: polytest.cpp:53
long left
Definition: polytest.cpp:53
BITMAPCOREHEADER bmciHeader
Definition: wingdi.h:1453
RGBTRIPLE bmciColors[1]
Definition: wingdi.h:1454
Definition: bl.h:1331
XLATEOBJ xlo
Definition: xlateobj.h:21
BASEOBJECT BaseObject
Definition: palette.h:36
ULONG NumColors
Definition: palette.h:41
PALETTEENTRY * IndexedColors
Definition: palette.h:42
FLONG flFlags
Definition: palette.h:40
LONG y
Definition: windef.h:330
LONG x
Definition: windef.h:329
LONG cx
Definition: kdterminal.h:27
LONG cy
Definition: kdterminal.h:28
SURFOBJ SurfObj
Definition: surface.h:8
HANDLE hSecure
Definition: surface.h:32
struct _PALETTE *const ppal
Definition: surface.h:11
USHORT fjBitmap
Definition: winddi.h:1217
SIZEL sizlBitmap
Definition: winddi.h:1209
PVOID pvBits
Definition: winddi.h:1211
ULONG iBitmapFormat
Definition: winddi.h:1215
Definition: parser.c:56
USHORT biBitCount
Definition: precomp.h:37
ULONG biCompression
Definition: precomp.h:38
BITMAPINFOHEADER bmiHeader
Definition: wingdi.h:1476
RGBQUAD bmiColors[1]
Definition: wingdi.h:1477
LONG right
Definition: windef.h:308
LONG bottom
Definition: windef.h:309
LONG top
Definition: windef.h:307
LONG left
Definition: windef.h:306
UCHAR rgbBlue
Definition: bootanim.c:97
UCHAR rgbRed
Definition: bootanim.c:99
UCHAR rgbGreen
Definition: bootanim.c:98
BYTE rgbtGreen
Definition: wingdi.h:1439
BYTE rgbtBlue
Definition: wingdi.h:1438
BYTE rgbtRed
Definition: wingdi.h:1440
#define max(a, b)
Definition: svc.c:63
#define WIDTH_BYTES_ALIGN32(cx, bpp)
Definition: swimpl.c:16
unsigned char * LPBYTE
Definition: typedefs.h:53
#define NTAPI
Definition: typedefs.h:36
void * PVOID
Definition: typedefs.h:50
PVOID HANDLE
Definition: typedefs.h:73
ULONG_PTR SIZE_T
Definition: typedefs.h:80
int32_t INT
Definition: typedefs.h:58
#define RtlCopyMemory(Destination, Source, Length)
Definition: typedefs.h:263
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:262
uint32_t ULONG_PTR
Definition: typedefs.h:65
#define IN
Definition: typedefs.h:39
uint32_t ULONG
Definition: typedefs.h:59
#define OUT
Definition: typedefs.h:40
char * PCHAR
Definition: typedefs.h:51
_In_ HFONT _Out_ PUINT _Out_ PUINT Width
Definition: font.h:89
_In_ HFONT _Out_ PUINT Height
Definition: font.h:88
static int __cdecl compr(const void *a, const void *b)
Definition: bidi.c:641
int ret
_Must_inspect_result_ _In_ WDFCHILDLIST _In_ PWDF_CHILD_LIST_ITERATOR _Out_ WDFDEVICE _Inout_opt_ PWDF_CHILD_RETRIEVE_INFO Info
Definition: wdfchildlist.h:690
HDC hdcMem
Definition: welcome.c:104
VOID DIB_1BPP_HLine(SURFOBJ *, LONG, LONG, LONG, ULONG)
Definition: dib1bpp.c:38
BOOL APIENTRY IntEngBitBlt(SURFOBJ *psoTrg, SURFOBJ *psoSrc, SURFOBJ *psoMask, CLIPOBJ *pco, XLATEOBJ *pxlo, RECTL *prclTrg, POINTL *pptlSrc, POINTL *pptlMask, BRUSHOBJ *pbo, POINTL *pptlBrush, ROP4 Rop4)
Definition: bitblt.c:656
VOID FASTCALL SetLastNtError(NTSTATUS Status)
Definition: error.c:37
ULONG FASTCALL BitmapFormat(ULONG cBits, ULONG iCompression)
Definition: surface.c:39
#define SURFACE_ShareUnlockSurface(pBMObj)
Definition: surface.h:102
FORCEINLINE VOID SURFACE_vSetPalette(_Inout_ PSURFACE psurf, _In_ PPALETTE ppal)
Definition: surface.h:136
@ API_BITMAP
Definition: surface.h:76
#define SURFACE_ShareLockSurface(hBMObj)
Definition: surface.h:91
#define BitsPerFormat(Format)
Definition: surface.h:109
#define DIB_PAL_BRUSHHACK
Definition: dib.h:36
BOOL NTAPI GreDeleteObject(HGDIOBJ hobj)
Definition: gdiobj.c:1158
PPALETTE NTAPI PALETTE_AllocPalWithHandle(_In_ ULONG iMode, _In_ ULONG cColors, _In_opt_ const PALETTEENTRY *pEntries, _In_ FLONG flRed, _In_ FLONG flGreen, _In_ FLONG flBlue)
Definition: palette.c:209
PPALETTE NTAPI PALETTE_AllocPalette(_In_ ULONG iMode, _In_ ULONG cColors, _In_opt_ const PALETTEENTRY *pEntries, _In_ FLONG flRed, _In_ FLONG flGreen, _In_ FLONG flBlue)
Definition: palette.c:135
PALETTE * gppalDefault
Definition: palette.c:20
#define PALETTE_UnlockPalette(pPalette)
Definition: palette.h:56
FORCEINLINE VOID PALETTE_vSetRGBColorForIndex(PPALETTE ppal, ULONG ulIndex, COLORREF crColor)
Definition: palette.h:152
@ PAL_BRUSHHACK
Definition: palette.h:23
#define PALETTE_ShareLockPalette(hpal)
Definition: palette.h:57
#define PALETTE_ShareUnlockPalette(ppal)
Definition: palette.h:59
FORCEINLINE ULONG PALETTE_ulGetRGBColorFromIndex(PPALETTE ppal, ULONG ulIndex)
Definition: palette.h:142
VOID FASTCALL RECTL_vMakeWellOrdered(_Inout_ RECTL *prcl)
Definition: rect.c:81
FORCEINLINE VOID RECTL_vSetRect(_Out_ RECTL *prcl, _In_ LONG left, _In_ LONG top, _In_ LONG right, _In_ LONG bottom)
Definition: rect.h:5
FORCEINLINE VOID RECTL_vOffsetRect(_Inout_ RECTL *prcl, _In_ INT cx, _In_ INT cy)
Definition: rect.h:31
#define TAG_DIB
Definition: tags.h:17
ENGAPI BOOL APIENTRY EngDeleteSurface(_In_ _Post_ptr_invalid_ HSURF hsurf)
Definition: surface.c:567
_In_ FLONG fl
Definition: winddi.h:1279
#define BMF_1BPP
Definition: winddi.h:355
#define PAL_BITFIELDS
Definition: winddi.h:1562
_In_ HANDLE hcmXform
Definition: winddi.h:3687
ENGAPI SURFOBJ *APIENTRY EngLockSurface(_In_ HSURF hsurf)
Definition: surface.c:607
#define BMF_DONTCACHE
Definition: winddi.h:1182
_In_ ULONG _In_ ULONG rgb
Definition: winddi.h:3521
ENGAPI VOID APIENTRY EngFreeUserMem(_Pre_notnull_ __drv_freesMem(UserMem) PVOID pv)
#define BMF_TOPDOWN
Definition: winddi.h:1180
#define BMF_USERMEM
Definition: winddi.h:1183
typedef HSURF(APIENTRY FN_DrvEnableSurface)(_In_ DHPDEV dhpdev)
ENGAPI VOID APIENTRY EngSetLastError(_In_ ULONG iError)
Definition: error.c:28
ENGAPI HANDLE APIENTRY EngSecureMem(_In_reads_bytes_(cjLength) PVOID Address, _In_ ULONG cjLength)
#define PAL_INDEXED
Definition: winddi.h:1561
#define BMF_NOZEROINIT
Definition: winddi.h:1181
ENGAPI VOID APIENTRY EngUnsecureMem(_In_ HANDLE hSecure)
ENGAPI VOID APIENTRY EngUnlockSurface(_In_ _Post_ptr_invalid_ SURFOBJ *pso)
Definition: surface.c:628
DWORD COLORREF
Definition: windef.h:300
#define ERROR_NO_SYSTEM_RESOURCES
Definition: winerror.h:931
_In_ const BITMAPINFO _In_ UINT _In_opt_ HANDLE hSection
Definition: wingdi.h:3239
struct _BITMAPCOREINFO * PBITMAPCOREINFO
#define DIB_RGB_COLORS
Definition: wingdi.h:367
#define DIB_PAL_COLORS
Definition: wingdi.h:366
#define SRCCOPY
Definition: wingdi.h:333
struct BITMAPV4HEADER * PBITMAPV4HEADER
#define CBM_INIT
Definition: wingdi.h:365
#define BI_RLE8
Definition: wingdi.h:35
static int init
Definition: wintirpc.c:33
VOID NTAPI EXLATEOBJ_vInitialize(_Out_ PEXLATEOBJ pexlo, _In_opt_ PALETTE *ppalSrc, _In_opt_ PALETTE *ppalDst, _In_ COLORREF crSrcBackColor, _In_ COLORREF crDstBackColor, _In_ COLORREF crDstForeColor)
Definition: xlateobj.c:358
VOID NTAPI EXLATEOBJ_vCleanup(_Inout_ PEXLATEOBJ pexlo)
Definition: xlateobj.c:649
unsigned char BYTE
Definition: xxhash.c:193