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