ReactOS 0.4.15-dev-7897-g78dc504
bitmap.c File Reference
#include <precomp.h>
#include <pseh/pseh2.h>
#include <debug.h>
Include dependency graph for bitmap.c:

Go to the source code of this file.

Macros

#define NDEBUG
 
#define WIDTH_BYTES_ALIGN32(cx, bpp)   ((((cx) * (bpp) + 31) & ~31) >> 3)
 
#define MaxScanLines   1000
 
#define MaxHeight   2000
 
#define MaxSourceHeight   2000
 
#define IS_ALIGNED(Pointer, Alignment)    (((ULONG_PTR)(void *)(Pointer)) % (Alignment) == 0)
 

Functions

ULONG FASTCALL BitmapFormat (ULONG cBits, ULONG iCompression)
 
INT FASTCALL DIB_BitmapInfoSize (const BITMAPINFO *info, WORD coloruse, BOOL max)
 
UINT FASTCALL DIB_BitmapMaxBitsSize (PBITMAPINFO Info, UINT ScanLines)
 
INT WINAPI DIB_GetBitmapInfo (const BITMAPINFOHEADER *header, PLONG width, PLONG height, PWORD planes, PWORD bpp, PLONG compr, PLONG size)
 
int WINAPI GdiGetBitmapBitsSize (BITMAPINFO *lpbmi)
 
HBITMAP WINAPI CreateDIBSection (HDC hDC, CONST BITMAPINFO *BitmapInfo, UINT Usage, VOID **Bits, HANDLE hSection, DWORD dwOffset)
 
HBITMAP WINAPI CreateBitmap (INT Width, INT Height, UINT Planes, UINT BitsPixel, CONST VOID *pUnsafeBits)
 
HBITMAP WINAPI CreateBitmapIndirect (const BITMAP *pbm)
 
HBITMAP WINAPI CreateDiscardableBitmap (HDC hDC, INT Width, INT Height)
 
HBITMAP WINAPI CreateCompatibleBitmap (HDC hDC, INT Width, INT Height)
 
INT WINAPI GetDIBits (HDC hDC, HBITMAP hbmp, UINT uStartScan, UINT cScanLines, LPVOID lpvBits, LPBITMAPINFO lpbmi, UINT uUsage)
 
HBITMAP WINAPI CreateDIBitmap (HDC hDC, const BITMAPINFOHEADER *Header, DWORD Init, LPCVOID Bits, const BITMAPINFO *Data, UINT ColorUse)
 
INT WINAPI SetDIBits (HDC hDC, HBITMAP hBitmap, UINT uStartScan, UINT cScanLines, CONST VOID *lpvBits, CONST BITMAPINFO *lpbmi, UINT fuColorUse)
 
INT WINAPI SetDIBitsToDevice (HDC hdc, int XDest, int YDest, DWORD Width, DWORD Height, int XSrc, int YSrc, UINT StartScan, UINT ScanLines, CONST VOID *Bits, CONST BITMAPINFO *lpbmi, UINT ColorUse)
 
int WINAPI StretchDIBits (HDC hdc, int XDest, int YDest, int nDestWidth, int nDestHeight, int XSrc, int YSrc, int nSrcWidth, int nSrcHeight, CONST VOID *lpBits, CONST BITMAPINFO *lpBitsInfo, UINT iUsage, DWORD dwRop)
 
DWORD WINAPI GetBitmapAttributes (HBITMAP hbm)
 
HBITMAP WINAPI SetBitmapAttributes (HBITMAP hbm, DWORD dwFlags)
 
HBITMAP WINAPI ClearBitmapAttributes (HBITMAP hbm, DWORD dwFlags)
 

Variables

UCHAR gajBitsPerFormat [11]
 

Macro Definition Documentation

◆ IS_ALIGNED

#define IS_ALIGNED (   Pointer,
  Alignment 
)     (((ULONG_PTR)(void *)(Pointer)) % (Alignment) == 0)

◆ MaxHeight

#define MaxHeight   2000

◆ MaxScanLines

#define MaxScanLines   1000

◆ MaxSourceHeight

#define MaxSourceHeight   2000

◆ NDEBUG

#define NDEBUG

Definition at line 5 of file bitmap.c.

◆ WIDTH_BYTES_ALIGN32

#define WIDTH_BYTES_ALIGN32 (   cx,
  bpp 
)    ((((cx) * (bpp) + 31) & ~31) >> 3)

Definition at line 55 of file bitmap.c.

Function Documentation

◆ BitmapFormat()

ULONG FASTCALL BitmapFormat ( ULONG  cBits,
ULONG  iCompression 
)

Definition at line 11 of file bitmap.c.

12{
13 switch (iCompression)
14 {
15 case BI_RGB:
16 /* Fall through */
17 case BI_BITFIELDS:
18 if (cBits <= 1) return BMF_1BPP;
19 if (cBits <= 4) return BMF_4BPP;
20 if (cBits <= 8) return BMF_8BPP;
21 if (cBits <= 16) return BMF_16BPP;
22 if (cBits <= 24) return BMF_24BPP;
23 if (cBits <= 32) return BMF_32BPP;
24 return 0;
25
26 case BI_RLE4:
27 return BMF_4RLE;
28
29 case BI_RLE8:
30 return BMF_8RLE;
31
32 default:
33 return 0;
34 }
35}
#define BI_RLE4
Definition: precomp.h:57
#define BI_RGB
Definition: precomp.h:56
#define BI_BITFIELDS
Definition: mmreg.h:507
#define BMF_16BPP
Definition: winddi.h:358
#define BMF_8BPP
Definition: winddi.h:357
#define BMF_1BPP
Definition: winddi.h:355
#define BMF_24BPP
Definition: winddi.h:359
#define BMF_32BPP
Definition: winddi.h:360
#define BMF_8RLE
Definition: winddi.h:362
#define BMF_4RLE
Definition: winddi.h:361
#define BMF_4BPP
Definition: winddi.h:356
#define BI_RLE8
Definition: wingdi.h:35

Referenced by SetDIBitsToDevice().

◆ ClearBitmapAttributes()

HBITMAP WINAPI ClearBitmapAttributes ( HBITMAP  hbm,
DWORD  dwFlags 
)

Definition at line 1199 of file bitmap.c.

1200{
1201 if ( dwFlags & ~SC_BB_STOCKOBJ )
1202 {
1203 return NULL;
1204 }
1206}
#define NULL
Definition: types.h:112
_In_ HBITMAP hbm
Definition: ntgdi.h:2776
__kernel_entry W32KAPI HBITMAP APIENTRY NtGdiClearBitmapAttributes(_In_ HBITMAP hbm, _In_ DWORD dwFlags)
#define SC_BB_STOCKOBJ
Definition: ntgdihdl.h:199
_In_ PCCERT_CONTEXT _In_ DWORD dwFlags
Definition: wincrypt.h:1176

Referenced by Test_BitmapAttributes().

◆ CreateBitmap()

HBITMAP WINAPI CreateBitmap ( INT  Width,
INT  Height,
UINT  Planes,
UINT  BitsPixel,
CONST VOID pUnsafeBits 
)

Definition at line 302 of file bitmap.c.

308{
309 if (Width && Height)
310 {
311 return NtGdiCreateBitmap(Width, Height, Planes, BitsPixel, (LPBYTE) pUnsafeBits);
312 }
313 else
314 {
315 /* Return 1x1 bitmap */
317 }
318}
__kernel_entry W32KAPI HBITMAP APIENTRY NtGdiCreateBitmap(_In_ INT cx, _In_ INT cy, _In_ UINT cPlanes, _In_ UINT cBPP, _In_opt_ LPBYTE pjInit)
#define DEFAULT_BITMAP
Definition: ntgdityp.h:195
unsigned char * LPBYTE
Definition: typedefs.h:53
_In_ HFONT _Out_ PUINT _Out_ PUINT Width
Definition: font.h:89
_In_ HFONT _Out_ PUINT Height
Definition: font.h:88
HGDIOBJ WINAPI GetStockObject(_In_ int)

◆ CreateBitmapIndirect()

HBITMAP WINAPI CreateBitmapIndirect ( const BITMAP pbm)

Definition at line 325 of file bitmap.c.

327{
329
330 /* Note windows xp/2003 does not check if pbm is NULL or not */
331 if ((pbm->bmWidthBytes != 0) && (!(pbm->bmWidthBytes & 1)))
332
333 {
334 bitmap = CreateBitmap(pbm->bmWidth, pbm->bmHeight, pbm->bmPlanes, pbm->bmBitsPixel,
335 pbm->bmBits);
336 }
337 else
338 {
340 }
341
342 return bitmap;
343}
#define ERROR_INVALID_PARAMETER
Definition: compat.h:101
#define SetLastError(x)
Definition: compat.h:752
static HBITMAP
Definition: button.c:44
Definition: uimain.c:89
HBITMAP WINAPI CreateBitmap(_In_ INT cx, _In_ INT cy, _In_ UINT cPlanes, _In_ UINT cBitsPerPel, _In_opt_ const VOID *pvBits)

◆ CreateCompatibleBitmap()

HBITMAP WINAPI CreateCompatibleBitmap ( HDC  hDC,
INT  Width,
INT  Height 
)

Definition at line 357 of file bitmap.c.

361{
362 PDC_ATTR pDc_Attr;
363
365 return NULL;
366
367 if (!Width || !Height)
369
370 if (!(pDc_Attr->ulDirty_ & DC_DIBSECTION))
371 {
373 }
374 else
375 {
376 HBITMAP hBmp = NULL;
377 struct
378 {
380 BITMAPINFOHEADER bmih;
381 RGBQUAD rgbquad[256];
382 } buffer;
383 DIBSECTION* pDIBs = (DIBSECTION*) &buffer;
384 BITMAPINFO* pbmi = (BITMAPINFO*) &buffer.bmih;
385
387
388 if (GetObjectA(hBmp, sizeof(DIBSECTION), pDIBs) != sizeof(DIBSECTION))
389 return NULL;
390
391 if (pDIBs->dsBm.bmBitsPixel <= 8)
392 GetDIBColorTable(hDC, 0, 256, buffer.rgbquad);
393
394 pDIBs->dsBmih.biWidth = Width;
395 pDIBs->dsBmih.biHeight = Height;
396
398 }
399 return NULL;
400}
static HDC hDC
Definition: 3dtext.c:33
ULONG RGBQUAD
Definition: precomp.h:59
#define GDI_OBJECT_TYPE_DC
Definition: gdi.h:46
#define GDI_OBJECT_TYPE_BITMAP
Definition: gdi.h:48
PVOID GdiGetHandleUserData(_In_ HGDIOBJ hobj)
Definition: gditools.c:68
GLuint buffer
Definition: glext.h:5915
__kernel_entry W32KAPI HBITMAP APIENTRY NtGdiCreateCompatibleBitmap(_In_ HDC hdc, _In_ INT cx, _In_ INT cy)
_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)
#define DC_DIBSECTION
Definition: ntgdihdl.h:137
Definition: bl.h:1331
WORD bmBitsPixel
Definition: wingdi.h:1426
BITMAP dsBm
Definition: wingdi.h:1669
BITMAPINFOHEADER dsBmih
Definition: wingdi.h:1670
HBITMAP WINAPI CreateDIBSection(HDC hDC, CONST BITMAPINFO *BitmapInfo, UINT Usage, VOID **Bits, HANDLE hSection, DWORD dwOffset)
Definition: bitmap.c:245
UINT WINAPI GetDIBColorTable(HDC hDC, UINT iStartIndex, UINT cEntries, RGBQUAD *pColors)
Definition: palette.c:123
#define DIB_RGB_COLORS
Definition: wingdi.h:367
int WINAPI GetObjectA(_In_ HANDLE h, _In_ int c, _Out_writes_bytes_opt_(c) LPVOID pv)

◆ CreateDIBitmap()

HBITMAP WINAPI CreateDIBitmap ( HDC  hDC,
const BITMAPINFOHEADER Header,
DWORD  Init,
LPCVOID  Bits,
const BITMAPINFO Data,
UINT  ColorUse 
)

Definition at line 448 of file bitmap.c.

455{
456 LONG Width, Height, Compression, DibSize;
457 WORD Planes, BitsPerPixel;
458// PDC_ATTR pDc_Attr;
459 UINT cjBmpScanSize = 0;
461 PBITMAPINFO pbmiConverted;
462 UINT cjInfoSize;
463
464 /* Convert the BITMAPINFO if it is a COREINFO */
465 pbmiConverted = ConvertBitmapInfo(Data, ColorUse, &cjInfoSize, FALSE);
466
467 /* Check for CBM_CREATDIB */
468 if (Init & CBM_CREATDIB)
469 {
470 if (cjInfoSize == 0)
471 {
472 goto Exit;
473 }
474 else if (Init & CBM_INIT)
475 {
476 if (Bits == NULL)
477 {
478 goto Exit;
479 }
480 }
481 else
482 {
483 Bits = NULL;
484 }
485
486 /* CBM_CREATDIB needs Data. */
487 if (pbmiConverted == NULL)
488 {
489 DPRINT1("CBM_CREATDIB needs a BITMAPINFO!\n");
490 goto Exit;
491 }
492
493 /* It only works with PAL or RGB */
494 if (ColorUse > DIB_PAL_COLORS)
495 {
496 DPRINT1("Invalid ColorUse: %lu\n", ColorUse);
498 goto Exit;
499 }
500
501 /* Use the header from the data */
502 Header = &Data->bmiHeader;
503 }
504 else
505 {
506 if (Init & CBM_INIT)
507 {
508 if (Bits != NULL)
509 {
510 if (cjInfoSize == 0)
511 {
512 goto Exit;
513 }
514 }
515 else
516 {
517 Init &= ~CBM_INIT;
518 }
519 }
520 }
521
522 /* Header is required */
523 if (!Header)
524 {
525 DPRINT1("Header is NULL\n");
527 goto Exit;
528 }
529
530 /* Get the bitmap format and dimensions */
531 if (DIB_GetBitmapInfo(Header, &Width, &Height, &Planes, &BitsPerPixel, &Compression, &DibSize) == -1)
532 {
533 DPRINT1("DIB_GetBitmapInfo failed!\n");
535 goto Exit;
536 }
537
538 /* Check if the Compr is incompatible */
539 if ((Compression == BI_JPEG) || (Compression == BI_PNG))
540 {
541 DPRINT1("Invalid compression: %lu!\n", Compression);
542 goto Exit;
543 }
544
545 /* Only DIB_RGB_COLORS (0), DIB_PAL_COLORS (1) and 2 are valid. */
546 if (ColorUse > DIB_PAL_COLORS + 1)
547 {
548 DPRINT1("Invalid compression: %lu!\n", Compression);
550 goto Exit;
551 }
552
553 /* If some Bits are given, only DIB_PAL_COLORS and DIB_RGB_COLORS are valid */
554 if (Bits && (ColorUse > DIB_PAL_COLORS))
555 {
556 DPRINT1("Invalid ColorUse: %lu\n", ColorUse);
558 goto Exit;
559 }
560
561 /* Negative width is not allowed */
562 if (Width < 0)
563 {
564 DPRINT1("Negative width: %li\n", Width);
565 goto Exit;
566 }
567
568 /* Top-down DIBs have a negative height. */
569 Height = abs(Height);
570
571// For Icm support.
572// GdiGetHandleUserData(hdc, GDI_OBJECT_TYPE_DC, (PVOID)&pDc_Attr))
573
574 cjBmpScanSize = GdiGetBitmapBitsSize(pbmiConverted);
575
576 DPRINT("pBMI %p, Size bpp %u, dibsize %d, Conv %u, BSS %u\n",
577 Data, BitsPerPixel, DibSize, cjInfoSize, cjBmpScanSize);
578
579 if (!Width || !Height)
580 {
582 }
583 else
584 {
586 Width,
587 Height,
588 Init,
589 (LPBYTE)Bits,
590 (LPBITMAPINFO)pbmiConverted,
591 ColorUse,
592 cjInfoSize,
593 cjBmpScanSize,
594 0, 0);
595 }
596
597Exit:
598 /* Cleanup converted BITMAPINFO */
599 if ((pbmiConverted != NULL) && (pbmiConverted != Data))
600 {
601 RtlFreeHeap(RtlGetProcessHeap(), 0, pbmiConverted);
602 }
603
604 return hBitmap;
605}
#define CBM_CREATDIB
#define DPRINT1
Definition: precomp.h:8
BOOLEAN NTAPI RtlFreeHeap(IN PVOID HeapHandle, IN ULONG Flags, IN PVOID HeapBase)
Definition: heap.c:608
Definition: Header.h:9
#define FALSE
Definition: types.h:117
static HBITMAP hBitmap
Definition: timezone.c:26
#define abs(i)
Definition: fconv.c:206
unsigned short WORD
Definition: ntddk_ex.h:93
LPBITMAPINFO WINAPI ConvertBitmapInfo(CONST BITMAPINFO *BitmapInfo, UINT ColorSpec, UINT *BitmapInfoSize, BOOL FollowedByData)
Definition: utils.c:178
VOID WINAPI GdiSetLastError(DWORD dwErrCode)
Definition: misc.c:873
unsigned int UINT
Definition: ndis.h:50
__kernel_entry W32KAPI HBITMAP APIENTRY NtGdiCreateDIBitmapInternal(_In_ HDC hdc, _In_ INT cx, _In_ INT cy, _In_ DWORD fInit, _In_reads_bytes_opt_(cjMaxBits) LPBYTE pjInit, _In_reads_bytes_opt_(cjMaxInitInfo) LPBITMAPINFO pbmi, _In_ DWORD iUsage, _In_ UINT cjMaxInitInfo, _In_ UINT cjMaxBits, _In_ FLONG f, _In_ HANDLE hcmXform)
long LONG
Definition: pedump.c:60
#define DPRINT
Definition: sndvol32.h:71
static void Exit(void)
Definition: sock.c:1330
int WINAPI GdiGetBitmapBitsSize(BITMAPINFO *lpbmi)
Definition: bitmap.c:209
INT WINAPI DIB_GetBitmapInfo(const BITMAPINFOHEADER *header, PLONG width, PLONG height, PWORD planes, PWORD bpp, PLONG compr, PLONG size)
Definition: bitmap.c:145
#define DIB_PAL_COLORS
Definition: wingdi.h:366
#define BI_JPEG
Definition: wingdi.h:38
#define CBM_INIT
Definition: wingdi.h:365
#define BI_PNG
Definition: wingdi.h:39

◆ CreateDIBSection()

HBITMAP WINAPI CreateDIBSection ( HDC  hDC,
CONST BITMAPINFO BitmapInfo,
UINT  Usage,
VOID **  Bits,
HANDLE  hSection,
DWORD  dwOffset 
)

Definition at line 245 of file bitmap.c.

252{
253 PBITMAPINFO pConvertedInfo;
254 UINT ConvertedInfoSize;
256 PVOID bmBits = NULL;
257
258 pConvertedInfo = ConvertBitmapInfo(BitmapInfo,
259 Usage,
260 &ConvertedInfoSize,
261 FALSE);
262 if (pConvertedInfo)
263 {
264 // Verify header due to converted may == info.
265 if (pConvertedInfo->bmiHeader.biSize >= sizeof(BITMAPINFOHEADER))
266 {
267 if (pConvertedInfo->bmiHeader.biCompression == BI_JPEG ||
268 pConvertedInfo->bmiHeader.biCompression == BI_PNG)
269 {
271 return NULL;
272 }
273 }
275 hSection,
276 dwOffset,
277 pConvertedInfo,
278 Usage,
279 ConvertedInfoSize,
280 0, // fl
281 0, // dwColorSpace
282 &bmBits);
283 if (!hBitmap)
284 bmBits = NULL;
285
286 if (BitmapInfo != pConvertedInfo)
287 RtlFreeHeap(RtlGetProcessHeap(), 0, pConvertedInfo);
288 }
289
290 if (Bits)
291 *Bits = bmBits;
292
293 return hBitmap;
294}
_Must_inspect_result_ _In_ USAGE _In_ USHORT _In_ USAGE Usage
Definition: hidpi.h:384
_In_ DWORD _In_ DWORD dwOffset
Definition: ntgdi.h:2033
__kernel_entry W32KAPI HBITMAP APIENTRY NtGdiCreateDIBSection(_In_ HDC hdc, _In_opt_ HANDLE hSectionApp, _In_ DWORD dwOffset, _In_reads_bytes_opt_(cjHeader) LPBITMAPINFO pbmi, _In_ DWORD iUsage, _In_ UINT cjHeader, _In_ FLONG fl, _In_ ULONG_PTR dwColorSpace, _Outptr_ PVOID *ppvBits)
ULONG biCompression
Definition: precomp.h:47
BITMAPINFOHEADER bmiHeader
Definition: wingdi.h:1476
_In_ const BITMAPINFO _In_ UINT _In_opt_ HANDLE hSection
Definition: wingdi.h:3239

Referenced by alpha_blend_hdc_pixels(), alpha_blend_image(), ARGB2BMP(), BITMAP_CopyImage(), BITMAP_LoadImageW(), BitmapFromClipboardDIB(), ConvertBitmapTo32Bpp(), ConvertToBlackAndWhite(), Create24BppBitmap(), Create32BitHBITMAP(), create_bitmap(), create_dib(), create_dib_section(), create_hatch_bitmap(), create_render_dc(), create_test_bitmap(), create_test_icon(), CreateCompatibleBitmap(), CreateDIBWithProperties(), CreateFrameBufferBitmap(), ATL::CImage::CreateInternal(), CShellLink::CreateShortcutIcon(), CreateStarBitmap(), draw_graphics(), DrawDibBegin(), DrawShadowText(), GdipCreateBitmapFromScan0(), GdipCreateHBITMAPFromBitmap(), GdipDrawImagePointsRect(), GdipGetDC(), get_bitmap_info(), ImageList_CreateImage(), Imm32LoadBitmapFromBytes(), InitBitmap(), InitLogo(), InitPerBitDepth(), IntCreate32BppBitmap(), mi_paint_rect(), mstsc_ProtocolIOThread(), OLEPictureImpl_LoadWICSource(), PaintCells(), PlayEnhMetaFileRecord(), CUIFBitmapDC::SetDIB(), START_TEST(), test_32bit_ddb(), test_alpha_hdc(), test_BitBlt(), test_bitmap_colors(), test_bitmap_font_glyph_index(), test_bitmap_rendering(), test_bitmapinfoheadersize(), test_boundsrect(), test_clipping(), test_color_table(), test_CopyImage_Bitmap(), test_CreateIcon(), test_data_handles(), test_device_caps(), test_dib_formats(), test_DIB_PAL_COLORS(), Test_Dibsection(), Test_DIBSectionEntry(), test_dibsections(), test_DrawDib_sizeimage(), test_DrawIcon(), test_DrawIconEx(), test_DrawState(), test_emf_BitBlt(), test_GdiAlphaBlend(), test_GdiGradientFill(), test_GdipCreateBitmapFromHBITMAP(), test_GetCursorFrameInfo(), Test_GetDIBColorTable(), test_GetDIBits_BI_BITFIELDS(), test_GetDIBits_scanlines(), test_GetDIBits_selected_DIB(), test_GetDIBits_top_down(), test_hdc_caching(), test_Image_StretchMode(), test_ImageList_DrawIndirect(), Test_MaskBlt_16bpp(), Test_MaskBlt_1bpp(), Test_MaskBlt_32bpp(), Test_MaskBlt_Brush(), test_mono_dibsection(), Test_NtGdiDoPalette_SetDIBColorTable(), test_palette_brush(), test_path_state(), test_pattern_brush(), Test_SelectDIBSection(), Test_SetDIBits(), test_SetDIBits(), test_SetDIBits_RLE4(), test_SetDIBits_RLE8(), test_SetDIBitsToDevice(), test_SetDIBitsToDevice_RLE8(), Test_SetPixel_PAL(), test_simple_graphics(), Test_SrcMono(), test_StretchBlt(), test_StretchBlt_TopDownOptions(), test_StretchDIBits(), test_WICCreateBitmapFromSectionEx(), UXTHEME_DrawThemePartToDib(), and WinGCreateBitmap().

◆ CreateDiscardableBitmap()

HBITMAP WINAPI CreateDiscardableBitmap ( HDC  hDC,
INT  Width,
INT  Height 
)

Definition at line 347 of file bitmap.c.

351{
353}
HBITMAP WINAPI CreateCompatibleBitmap(_In_ HDC hdc, _In_ INT cx, _In_ INT cy)

◆ DIB_BitmapInfoSize()

INT FASTCALL DIB_BitmapInfoSize ( const BITMAPINFO info,
WORD  coloruse,
BOOL  max 
)

Definition at line 65 of file bitmap.c.

69{
70 unsigned int colors, size, masks = 0;
71
72 if (info->bmiHeader.biSize == sizeof(BITMAPCOREHEADER))
73 {
74 const BITMAPCOREHEADER *core = (const BITMAPCOREHEADER *) info;
75 size = sizeof(BITMAPCOREHEADER);
76 if (core->bcBitCount <= 8)
77 {
78 colors = 1 << core->bcBitCount;
79 if (coloruse == DIB_RGB_COLORS)
80 size += colors * sizeof(RGBTRIPLE);
81 else
82 size += colors * sizeof(WORD);
83 }
84 return size;
85 }
86 else /* assume BITMAPINFOHEADER */
87 {
88 colors = max ? (1 << info->bmiHeader.biBitCount) : info->bmiHeader.biClrUsed;
89 if (colors > 256)
90 colors = 256;
91 if (!colors && (info->bmiHeader.biBitCount <= 8))
92 colors = 1 << info->bmiHeader.biBitCount;
93 if (info->bmiHeader.biCompression == BI_BITFIELDS)
94 masks = 3;
95 size = max(info->bmiHeader.biSize, sizeof(BITMAPINFOHEADER) + masks * sizeof(DWORD));
96 return size + colors * ((coloruse == DIB_RGB_COLORS) ? sizeof(RGBQUAD) : sizeof(WORD));
97 }
98}
unsigned long DWORD
Definition: ntddk_ex.h:95
GLsizeiptr size
Definition: glext.h:5919
if(dx< 0)
Definition: linetemp.h:194
static const BYTE masks[8]
Definition: dib.c:2760
#define max(a, b)
Definition: svc.c:63
struct tagRGBTRIPLE RGBTRIPLE
struct tagBITMAPCOREHEADER BITMAPCOREHEADER
ActualNumberDriverObjects * sizeof(PDRIVER_OBJECT)) PDRIVER_OBJECT *DriverObjectList

Referenced by GetDIBits(), IntSynthesizeBitmap(), and IntSynthesizeDib().

◆ DIB_BitmapMaxBitsSize()

UINT FASTCALL DIB_BitmapMaxBitsSize ( PBITMAPINFO  Info,
UINT  ScanLines 
)

Definition at line 107 of file bitmap.c.

110{
111 UINT Ret;
112
113 if (!Info)
114 return 0;
115
116 if (Info->bmiHeader.biSize == sizeof(BITMAPCOREHEADER))
117 {
119 Ret = WIDTH_BYTES_ALIGN32(Core->bcWidth * Core->bcPlanes,
120 Core->bcBitCount) * ScanLines;
121 }
122 else /* assume BITMAPINFOHEADER */
123 {
124 if ((Info->bmiHeader.biCompression == BI_RGB) || (Info->bmiHeader.biCompression == BI_BITFIELDS))
125 {
127 Info->bmiHeader.biWidth * Info->bmiHeader.biPlanes,
128 Info->bmiHeader.biBitCount) * ScanLines;
129 }
130 else
131 {
132 Ret = Info->bmiHeader.biSizeImage;
133 }
134 }
135 return Ret;
136}
_Must_inspect_result_ _In_ WDFCHILDLIST _In_ PWDF_CHILD_LIST_ITERATOR _Out_ WDFDEVICE _Inout_opt_ PWDF_CHILD_RETRIEVE_INFO Info
Definition: wdfchildlist.h:690
#define WIDTH_BYTES_ALIGN32(cx, bpp)
Definition: bitmap.c:55
struct tagBITMAPCOREHEADER * PBITMAPCOREHEADER

Referenced by GetDIBits(), and SetDIBitsToDevice().

◆ DIB_GetBitmapInfo()

INT WINAPI DIB_GetBitmapInfo ( const BITMAPINFOHEADER header,
PLONG  width,
PLONG  height,
PWORD  planes,
PWORD  bpp,
PLONG  compr,
PLONG  size 
)

Definition at line 145 of file bitmap.c.

153{
154 if (header->biSize == sizeof(BITMAPCOREHEADER))
155 {
157 *width = core->bcWidth;
158 *height = core->bcHeight;
159 *planes = core->bcPlanes;
160 *bpp = core->bcBitCount;
161 *compr = 0;
162 *size = 0;
163 return 0;
164 }
165
166 if (header->biSize == sizeof(BITMAPINFOHEADER))
167 {
168 *width = header->biWidth;
169 *height = header->biHeight;
170 *planes = header->biPlanes;
171 *bpp = header->biBitCount;
172 *compr = header->biCompression;
173 *size = header->biSizeImage;
174 return 1;
175 }
176
177 if (header->biSize == sizeof(BITMAPV4HEADER))
178 {
180 *width = v4hdr->bV4Width;
181 *height = v4hdr->bV4Height;
182 *planes = v4hdr->bV4Planes;
183 *bpp = v4hdr->bV4BitCount;
184 *compr = v4hdr->bV4V4Compression;
185 *size = v4hdr->bV4SizeImage;
186 return 4;
187 }
188
189 if (header->biSize == sizeof(BITMAPV5HEADER))
190 {
191 BITMAPV5HEADER *v5hdr = (BITMAPV5HEADER *) header;
192 *width = v5hdr->bV5Width;
193 *height = v5hdr->bV5Height;
194 *planes = v5hdr->bV5Planes;
195 *bpp = v5hdr->bV5BitCount;
196 *compr = v5hdr->bV5Compression;
197 *size = v5hdr->bV5SizeImage;
198 return 5;
199 }
200 DPRINT("(%lu): wrong size for header\n", header->biSize);
201 return -1;
202}
DWORD bpp
Definition: surface.c:185
GLint GLint GLsizei GLsizei height
Definition: gl.h:1546
GLint GLint GLsizei width
Definition: gl.h:1546
WORD bV4Planes
Definition: wingdi.h:1495
DWORD bV4SizeImage
Definition: wingdi.h:1498
DWORD bV4V4Compression
Definition: wingdi.h:1497
LONG bV4Height
Definition: wingdi.h:1494
LONG bV4Width
Definition: wingdi.h:1493
WORD bV4BitCount
Definition: wingdi.h:1496
static int __cdecl compr(const void *a, const void *b)
Definition: bidi.c:641

Referenced by CreateDIBitmap().

◆ GdiGetBitmapBitsSize()

int WINAPI GdiGetBitmapBitsSize ( BITMAPINFO lpbmi)

Definition at line 209 of file bitmap.c.

211{
212 UINT Ret;
213
214 if (!lpbmi)
215 return 0;
216
217 if (lpbmi->bmiHeader.biSize == sizeof(BITMAPCOREHEADER))
218 {
220 Ret =
222 Core->bcBitCount) * Core->bcHeight;
223 }
224 else /* assume BITMAPINFOHEADER */
225 {
226 if (!(lpbmi->bmiHeader.biCompression) || (lpbmi->bmiHeader.biCompression == BI_BITFIELDS))
227 {
229 lpbmi->bmiHeader.biWidth * lpbmi->bmiHeader.biPlanes,
230 lpbmi->bmiHeader.biBitCount) * abs(lpbmi->bmiHeader.biHeight);
231 }
232 else
233 {
234 Ret = lpbmi->bmiHeader.biSizeImage;
235 }
236 }
237 return Ret;
238}
USHORT biBitCount
Definition: precomp.h:46

Referenced by ConvertBitmapInfo(), CreateDIBitmap(), and StretchDIBits().

◆ GetBitmapAttributes()

DWORD WINAPI GetBitmapAttributes ( HBITMAP  hbm)

Definition at line 1171 of file bitmap.c.

1172{
1174 {
1175 return SC_BB_STOCKOBJ;
1176 }
1177 return 0;
1178}
#define GDI_HANDLE_IS_STOCKOBJ(h)
Definition: gdi.h:37

Referenced by Test_BitmapAttributes().

◆ GetDIBits()

INT WINAPI GetDIBits ( HDC  hDC,
HBITMAP  hbmp,
UINT  uStartScan,
UINT  cScanLines,
LPVOID  lpvBits,
LPBITMAPINFO  lpbmi,
UINT  uUsage 
)

Definition at line 404 of file bitmap.c.

412{
413 UINT cjBmpScanSize;
414 UINT cjInfoSize;
415
416 if (!hDC || !GdiValidateHandle((HGDIOBJ) hDC) || !lpbmi)
417 {
419 return 0;
420 }
421
422 cjBmpScanSize = DIB_BitmapMaxBitsSize(lpbmi, cScanLines);
423 /* Caller must provide maximum size possible */
424 cjInfoSize = DIB_BitmapInfoSize(lpbmi, uUsage, TRUE);
425
426 if (lpvBits)
427 {
428 if (lpbmi->bmiHeader.biSize >= sizeof(BITMAPINFOHEADER))
429 {
430 if (lpbmi->bmiHeader.biCompression == BI_JPEG
431 || lpbmi->bmiHeader.biCompression == BI_PNG)
432 {
434 return 0;
435 }
436 }
437 }
438
439 return NtGdiGetDIBitsInternal(hDC, hbmp, uStartScan, cScanLines, lpvBits, lpbmi, uUsage,
440 cjBmpScanSize, cjInfoSize);
441}
HBITMAP hbmp
#define TRUE
Definition: types.h:120
BOOL WINAPI GdiValidateHandle(HGDIOBJ)
Definition: misc.c:712
UINT FASTCALL DIB_BitmapMaxBitsSize(PBITMAPINFO Info, UINT ScanLines)
Definition: bitmap.c:107
INT FASTCALL DIB_BitmapInfoSize(const BITMAPINFO *info, WORD coloruse, BOOL max)
Definition: bitmap.c:65

◆ SetBitmapAttributes()

HBITMAP WINAPI SetBitmapAttributes ( HBITMAP  hbm,
DWORD  dwFlags 
)

Definition at line 1185 of file bitmap.c.

1186{
1187 if ( dwFlags & ~SC_BB_STOCKOBJ )
1188 {
1189 return NULL;
1190 }
1192}
__kernel_entry W32KAPI HBITMAP APIENTRY NtGdiSetBitmapAttributes(_In_ HBITMAP hbm, _In_ DWORD dwFlags)

Referenced by Test_BitmapAttributes().

◆ SetDIBits()

INT WINAPI SetDIBits ( HDC  hDC,
HBITMAP  hBitmap,
UINT  uStartScan,
UINT  cScanLines,
CONST VOID lpvBits,
CONST BITMAPINFO lpbmi,
UINT  fuColorUse 
)

Definition at line 612 of file bitmap.c.

620{
621 HDC hDCc, SavehDC, nhDC;
623 HGDIOBJ hOldBitmap;
624 HPALETTE hPal = NULL;
625 INT LinesCopied = 0;
626 BOOL newDC = FALSE;
627
628 if (fuColorUse != DIB_RGB_COLORS && fuColorUse != DIB_PAL_COLORS)
629 return 0;
630
632 return 0;
633
634 if (lpbmi->bmiHeader.biSize >= sizeof(BITMAPINFOHEADER))
635 {
636 if (lpbmi->bmiHeader.biCompression == BI_JPEG
637 || lpbmi->bmiHeader.biCompression == BI_PNG)
638 {
640 return 0;
641 }
642 }
643
644 if (lpbmi->bmiHeader.biCompression == BI_BITFIELDS)
645 {
646 DWORD *masks = (DWORD *)lpbmi->bmiColors;
647 if (!masks[0] || !masks[1] || !masks[2])
648 {
650 return 0;
651 }
652 }
653
654 hDCc = NtGdiGetDCforBitmap(hBitmap); // hDC can be NULL, so, get it from the bitmap.
655 SavehDC = hDCc;
656 if (!hDCc) // No DC associated with bitmap, Clone or Create one.
657 {
658 nhDC = CreateCompatibleDC(hDC);
659 if (!nhDC)
660 return 0;
661 newDC = TRUE;
662 SavehDC = nhDC;
663 }
664 else if (!SaveDC(hDCc))
665 return 0;
666
667 hOldBitmap = SelectObject(SavehDC, hBitmap);
668
669 if (hOldBitmap)
670 {
671 if (hDC)
672 hPal = SelectPalette(SavehDC, (HPALETTE) GetCurrentObject(hDC, OBJ_PAL), FALSE);
673
674 if (lpbmi->bmiHeader.biSize < sizeof(BITMAPINFOHEADER))
675 {
676 PBITMAPCOREINFO pbci = (PBITMAPCOREINFO) lpbmi;
677 dwWidth = pbci->bmciHeader.bcWidth;
679 }
680 else
681 {
682 dwWidth = lpbmi->bmiHeader.biWidth;
683 dwHeight = abs(lpbmi->bmiHeader.biHeight);
684 }
685
686 LinesCopied = SetDIBitsToDevice(SavehDC, 0, 0, dwWidth, dwHeight, 0, 0, uStartScan,
687 cScanLines, (void *) lpvBits, (LPBITMAPINFO) lpbmi, fuColorUse);
688
689 if (hDC)
690 SelectPalette(SavehDC, hPal, FALSE);
691
692 SelectObject(SavehDC, hOldBitmap);
693 }
694
695 if (newDC)
696 DeleteDC(SavehDC);
697 else
698 RestoreDC(SavehDC, -1);
699
700 return LinesCopied;
701}
static const WCHAR dwWidth[]
Definition: provider.c:62
static const WCHAR dwHeight[]
Definition: provider.c:63
unsigned int BOOL
Definition: ntddk_ex.h:94
#define GDI_HANDLE_GET_TYPE(h)
Definition: gdi.h:31
static HDC
Definition: bitmap.c:44
__kernel_entry W32KAPI HDC APIENTRY NtGdiGetDCforBitmap(_In_ HBITMAP hsurf)
#define OBJ_PAL
Definition: objidl.idl:1413
BITMAPCOREHEADER bmciHeader
Definition: wingdi.h:1453
int32_t INT
Definition: typedefs.h:58
struct _BITMAPCOREINFO * PBITMAPCOREINFO
int WINAPI SetDIBitsToDevice(_In_ HDC, _In_ int, _In_ int, _In_ DWORD, _In_ DWORD, _In_ int, _In_ int, _In_ UINT, _In_ UINT, _In_ CONST VOID *, _In_ CONST BITMAPINFO *, _In_ UINT)
HPALETTE WINAPI SelectPalette(_In_ HDC, _In_ HPALETTE, _In_ BOOL)
HGDIOBJ WINAPI GetCurrentObject(_In_ HDC, _In_ UINT)
Definition: dc.c:428
HGDIOBJ WINAPI SelectObject(_In_ HDC, _In_ HGDIOBJ)
Definition: dc.c:1539
HDC WINAPI CreateCompatibleDC(_In_opt_ HDC hdc)
BOOL WINAPI RestoreDC(_In_ HDC, _In_ int)
BOOL WINAPI DeleteDC(_In_ HDC)
int WINAPI SaveDC(_In_ HDC)

◆ SetDIBitsToDevice()

INT WINAPI SetDIBitsToDevice ( HDC  hdc,
int  XDest,
int  YDest,
DWORD  Width,
DWORD  Height,
int  XSrc,
int  YSrc,
UINT  StartScan,
UINT  ScanLines,
CONST VOID Bits,
CONST BITMAPINFO lpbmi,
UINT  ColorUse 
)

Definition at line 709 of file bitmap.c.

722{
723 PDC_ATTR pDc_Attr;
724 PBITMAPINFO pConvertedInfo;
725 UINT ConvertedInfoSize;
726 INT LinesCopied = 0;
727 UINT cjBmpScanSize = 0;
728 BOOL Hit = FALSE;
729 PVOID pvSafeBits = (PVOID) Bits;
730 UINT bmiHeight;
731 BOOL top_down;
732 INT src_y = 0;
733 ULONG iFormat, cBitsPixel, cjBits, cjWidth;
734
735 #define MaxScanLines 1000
736 #define MaxHeight 2000
737 #define MaxSourceHeight 2000
738 #define IS_ALIGNED(Pointer, Alignment) \
739 (((ULONG_PTR)(void *)(Pointer)) % (Alignment) == 0)
740
741 if (!ScanLines || !lpbmi || !Bits)
742 return 0;
743
744 DPRINT("ScanLines %d Height %d Width %d biHeight %d biWidth %d\n"
745 " lpbmi '%p' ColorUse '%d' SizeImage '%d' StartScan %d\n"
746 " biCompression '%d' biBitCount '%d'\n",
747 ScanLines, Height, Width, lpbmi->bmiHeader.biHeight,
748 lpbmi->bmiHeader.biWidth, lpbmi, ColorUse,
749 lpbmi->bmiHeader.biSizeImage, StartScan,
750 lpbmi->bmiHeader.biCompression, lpbmi->bmiHeader.biBitCount);
751
752 if (lpbmi->bmiHeader.biWidth < 0)
753 return 0;
754
755 if (ColorUse && ColorUse != DIB_PAL_COLORS && ColorUse != DIB_PAL_COLORS + 1)
756 return 0;
757
758 pConvertedInfo = ConvertBitmapInfo(lpbmi, ColorUse, &ConvertedInfoSize, FALSE);
759 if (!pConvertedInfo)
760 return 0;
761
762 if (ScanLines > MaxScanLines)
763 {
764 LinesCopied = 0;
765 goto Exit;
766 }
767
768 bmiHeight = abs(pConvertedInfo->bmiHeader.biHeight);
769 top_down = (pConvertedInfo->bmiHeader.biHeight < 0);
770 if ((StartScan > bmiHeight) && (ScanLines > bmiHeight))
771 {
772 DPRINT("Returning ScanLines of '%d'\n", ScanLines);
773 LinesCopied = ScanLines;
774 goto Exit;
775 }
776
777 if (pConvertedInfo->bmiHeader.biHeight == 0)
778 {
779 LinesCopied = 0;
780 goto Exit;
781 }
782
783 if (!IS_ALIGNED(Bits, 2) && (ScanLines > Height))
784 {
785 LinesCopied = 0;
786 goto Exit;
787 }
788
789 /* Below code modeled after Wine's nulldrv_SetDIBitsToDevice */
790 if (StartScan <= YSrc + bmiHeight)
791 {
792 if ((pConvertedInfo->bmiHeader.biCompression == BI_RLE8) ||
793 (pConvertedInfo->bmiHeader.biCompression == BI_RLE4))
794 {
795 StartScan = 0;
796 ScanLines = bmiHeight;
797 }
798 else
799 {
800 if (StartScan >= bmiHeight)
801 {
802 LinesCopied = 0;
803 goto Exit;
804 }
805 if (!top_down && ScanLines > bmiHeight - StartScan)
806 {
807 ScanLines = bmiHeight - StartScan;
808 }
809 src_y = StartScan + ScanLines - (YSrc + Height);
810 if (!top_down)
811 {
812 /* get rid of unnecessary lines */
813 if ((src_y < 0 || src_y >= (INT)ScanLines) &&
814 pConvertedInfo->bmiHeader.biCompression != BI_BITFIELDS)
815 {
816 LinesCopied = ScanLines;
817 goto Exit;
818 }
819 if (YDest >= 0)
820 {
821 LinesCopied = ScanLines + StartScan;
822 ScanLines -= src_y;
823 }
824 else
825 {
826 LinesCopied = ScanLines - src_y;
827 }
828 }
829 else if (src_y < 0 || src_y >= (INT)ScanLines)
830 {
831 if (lpbmi->bmiHeader.biHeight < 0 &&
832 StartScan > MaxScanLines)
833 {
834 ScanLines = lpbmi->bmiHeader.biHeight - StartScan;
835 }
836 DPRINT("Returning ScanLines of '%d'\n", ScanLines);
837 LinesCopied = ScanLines;
838 goto Exit;
839 }
840 else
841 {
842 LinesCopied = ScanLines;
843 }
844 }
845 }
846
849 0,
850 hdc,
851 XDest,
852 YDest,
853 Width,
854 Height,
855 XSrc,
856 YSrc,
857 StartScan,
858 ScanLines,
859 Bits,
860 lpbmi,
861 ColorUse);
862
863 // Handle the "Special Case"!
864 {
865 PLDC pldc;
868 {
869 pldc = GdiGetLDC(hdc);
870 if (pldc)
871 {
872 if (pldc->Flags & LDC_STARTPAGE) StartPage(hdc);
873
874 if (pldc->Flags & LDC_SAPCALLBACK) GdiSAPCallback(pldc);
875
876 if (pldc->Flags & LDC_KILL_DOCUMENT)
877 {
878 LinesCopied = 0;
879 goto Exit;
880 }
881 }
882 else
883 {
885 LinesCopied = 0;
886 goto Exit;
887 }
888 }
889 }
890
891 if ((pConvertedInfo->bmiHeader.biCompression == BI_RLE8) ||
892 (pConvertedInfo->bmiHeader.biCompression == BI_RLE4))
893 {
894 /* For compressed data, we must set the whole thing */
895 StartScan = 0;
896 ScanLines = pConvertedInfo->bmiHeader.biHeight;
897 }
898
899 cjBmpScanSize = DIB_BitmapMaxBitsSize((LPBITMAPINFO) lpbmi, ScanLines);
900
901 pvSafeBits = RtlAllocateHeap(GetProcessHeap(), 0, cjBmpScanSize);
902 if (pvSafeBits)
903 {
905 {
906 RtlCopyMemory(pvSafeBits, Bits, cjBmpScanSize);
907 }
909 {
910 Hit = TRUE;
911 }
912 _SEH2_END;
913
914 if (Hit)
915 {
916 // We don't die, we continue on with a allocated safe pointer to kernel
917 // space.....
918
919 if (!IS_ALIGNED(Bits, 2)) // If both Read Exception and mis-aligned
920 {
921 LinesCopied = 0;
922 goto Exit;
923 }
924
925 DPRINT1("SetDIBitsToDevice fail to read BitMapInfo: %p or Bits: %p & Size: %u\n",
926 pConvertedInfo, Bits, cjBmpScanSize);
927 }
928 DPRINT("SetDIBitsToDevice Allocate Bits %u!!!\n", cjBmpScanSize);
929 }
930
932 {
933 DPRINT1("SetDIBitsToDevice called on invalid DC %p (not owned?)\n", hdc);
935 LinesCopied = 0;
936 goto Exit;
937 }
938
939 /* Calculation of ScanLines for NtGdiSetDIBitsToDeviceInternal */
940 if (YDest >= 0)
941 {
942 ScanLines = min(abs(Height), ScanLines);
943 if (YSrc > 0)
944 ScanLines += YSrc;
945 }
946 else
947 {
948 ScanLines = min(ScanLines,
949 abs(pConvertedInfo->bmiHeader.biHeight) - StartScan);
950 }
951
952 if (YDest >= 0 && YSrc > 0 && bmiHeight <= MaxHeight)
953 {
954 ScanLines += YSrc;
955 }
956
957 /* Find Format from lpbmi which is now pConvertedInfo */
958 iFormat = BitmapFormat(pConvertedInfo->bmiHeader.biBitCount,
959 pConvertedInfo->bmiHeader.biCompression);
960
961 /* Get bits per pixel from the format */
962 cBitsPixel = gajBitsPerFormat[iFormat];
963
964 cjWidth = WIDTH_BYTES_ALIGN32(pConvertedInfo->bmiHeader.biWidth, cBitsPixel);
965
966 /* Calculate the correct bitmap size in bytes */
967 if (!NT_SUCCESS(RtlULongMult(cjWidth, max(ScanLines, LinesCopied), &cjBits)))
968 {
969 DPRINT1("Overflow calculating size: cjWidth %lu, ScanLines %lu\n",
970 cjWidth, max(ScanLines, LinesCopied));
971 goto Exit;
972 }
973
974 /* Make sure the buffer is large enough */
975 if (pConvertedInfo->bmiHeader.biSizeImage < cjBits)
976 {
977 DPRINT("Buffer is too small, required: %lu, got %lu\n",
978 cjBits, pConvertedInfo->bmiHeader.biSizeImage);
979 if (pConvertedInfo->bmiHeader.biCompression == BI_RGB)
980 {
981 pConvertedInfo->bmiHeader.biSizeImage = cjBits;
982 }
983 }
984
985 /*
986 if ( !pDc_Attr || // DC is Public
987 ColorUse == DIB_PAL_COLORS ||
988 ((pConvertedInfo->bmiHeader.biSize >= sizeof(BITMAPINFOHEADER)) &&
989 (pConvertedInfo->bmiHeader.biCompression == BI_JPEG ||
990 pConvertedInfo->bmiHeader.biCompression == BI_PNG )) )*/
991 {
992 LinesCopied = NtGdiSetDIBitsToDeviceInternal(hdc, XDest, YDest,
993 Width, Height, XSrc, YSrc,
994 StartScan, ScanLines, (LPBYTE) pvSafeBits,
995 (LPBITMAPINFO) pConvertedInfo, ColorUse,
996 cjBmpScanSize, ConvertedInfoSize,
997 TRUE,
998 NULL);
999 }
1000
1001 if (bmiHeight > MaxScanLines)
1002 {
1003 LinesCopied = ScanLines;
1004 }
1005
1006 if (YDest < 0)
1007 {
1008 if (top_down)
1009 LinesCopied = ScanLines;
1010 else
1011 LinesCopied = ScanLines - src_y;
1012 }
1013
1014 if (pConvertedInfo->bmiHeader.biCompression == BI_RLE8 ||
1015 pConvertedInfo->bmiHeader.biCompression == BI_RLE4)
1016 {
1017 LinesCopied = bmiHeight;
1018 }
1019
1020 if (pConvertedInfo->bmiHeader.biHeight < 0)
1021 {
1022 if (pConvertedInfo->bmiHeader.biHeight < -MaxSourceHeight ||
1023 (YDest >= 0 && src_y < -ScanLines))
1024 {
1025 LinesCopied = ScanLines + src_y;
1026 }
1027 else
1028 {
1029 LinesCopied = ScanLines;
1030 }
1031 }
1032
1033Exit:
1034 if (Bits != pvSafeBits)
1035 RtlFreeHeap(RtlGetProcessHeap(), 0, pvSafeBits);
1036 if (lpbmi != pConvertedInfo)
1037 RtlFreeHeap(RtlGetProcessHeap(), 0, pConvertedInfo);
1038
1039 return LinesCopied;
1040}
PVOID NTAPI RtlAllocateHeap(IN PVOID HeapHandle, IN ULONG Flags, IN SIZE_T Size)
Definition: heap.c:590
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
#define GetProcessHeap()
Definition: compat.h:736
#define ERROR_INVALID_HANDLE
Definition: compat.h:98
#define _SEH2_END
Definition: filesup.c:22
#define _SEH2_TRY
Definition: filesup.c:19
VOID GdiSAPCallback(PLDC pldc)
Definition: misc.c:819
#define HANDLE_METADC(_RetType, _Func, dwError, hdc,...)
Definition: gdi32p.h:589
PLDC FASTCALL GdiGetLDC(HDC hDC)
Definition: misc.c:785
@ GDILoObjType_LO_METADC16_TYPE
Definition: gdi_private.h:49
@ GDILoObjType_LO_DC_TYPE
Definition: gdi_private.h:34
#define EXCEPTION_EXECUTE_HANDLER
Definition: excpt.h:85
HDC hdc
Definition: main.c:9
#define min(a, b)
Definition: monoChain.cc:55
__kernel_entry W32KAPI INT APIENTRY NtGdiSetDIBitsToDeviceInternal(_In_ HDC hdcDest, _In_ INT xDst, _In_ INT yDst, _In_ DWORD cx, _In_ DWORD cy, _In_ INT xSrc, _In_ INT ySrc, _In_ DWORD iStartScan, _In_ DWORD cNumScan, _In_reads_bytes_(cjMaxBits) LPBYTE pInitBits, _In_reads_bytes_(cjMaxInfo) LPBITMAPINFO pbmi, _In_ DWORD iUsage, _In_ UINT cjMaxBits, _In_ UINT cjMaxInfo, _In_ BOOL bTransformCoordinates, _In_opt_ HANDLE hcmXform)
#define LDC_KILL_DOCUMENT
Definition: ntgdihdl.h:158
#define LDC_SAPCALLBACK
Definition: ntgdihdl.h:150
#define LDC_STARTPAGE
Definition: ntgdihdl.h:153
#define _SEH2_EXCEPT(...)
Definition: pseh2_64.h:34
Definition: ntgdihdl.h:263
ULONG Flags
Definition: ntgdihdl.h:265
void * PVOID
Definition: typedefs.h:50
#define RtlCopyMemory(Destination, Source, Length)
Definition: typedefs.h:263
uint32_t ULONG
Definition: typedefs.h:59
UCHAR gajBitsPerFormat[11]
Definition: bitmap.c:39
#define MaxScanLines
ULONG FASTCALL BitmapFormat(ULONG cBits, ULONG iCompression)
Definition: bitmap.c:11
#define MaxHeight
#define IS_ALIGNED(Pointer, Alignment)
#define MaxSourceHeight
_In_ SIZEL _In_ ULONG iFormat
Definition: winddi.h:3468
int WINAPI StartPage(_In_ HDC)

◆ StretchDIBits()

int WINAPI StretchDIBits ( HDC  hdc,
int  XDest,
int  YDest,
int  nDestWidth,
int  nDestHeight,
int  XSrc,
int  YSrc,
int  nSrcWidth,
int  nSrcHeight,
CONST VOID lpBits,
CONST BITMAPINFO lpBitsInfo,
UINT  iUsage,
DWORD  dwRop 
)

Definition at line 1047 of file bitmap.c.

1062{
1063 PDC_ATTR pDc_Attr;
1064 PBITMAPINFO pConvertedInfo = NULL;
1065 UINT ConvertedInfoSize = 0;
1066 INT LinesCopied = 0;
1067 UINT cjBmpScanSize = 0;
1068 PVOID pvSafeBits = NULL;
1069 BOOL Hit = FALSE;
1070
1071 DPRINT("StretchDIBits %p : %p : %u\n", lpBits, lpBitsInfo, iUsage);
1072
1073 HANDLE_METADC( int,
1075 0,
1076 hdc,
1077 XDest,
1078 YDest,
1079 nDestWidth,
1080 nDestHeight,
1081 XSrc,
1082 YSrc,
1083 nSrcWidth,
1084 nSrcHeight,
1085 lpBits,
1086 lpBitsInfo,
1087 iUsage,
1088 dwRop );
1089
1090 if ( GdiConvertAndCheckDC(hdc) == NULL ) return 0;
1091
1092 pConvertedInfo = ConvertBitmapInfo(lpBitsInfo, iUsage, &ConvertedInfoSize, FALSE);
1093 if (!pConvertedInfo)
1094 {
1095 return 0;
1096 }
1097
1098 cjBmpScanSize = GdiGetBitmapBitsSize((BITMAPINFO *) pConvertedInfo);
1099
1100 if (lpBits)
1101 {
1102 pvSafeBits = RtlAllocateHeap(GetProcessHeap(), 0, cjBmpScanSize);
1103 if (pvSafeBits)
1104 {
1105 _SEH2_TRY
1106 {
1107 RtlCopyMemory(pvSafeBits, lpBits, cjBmpScanSize);
1108 }
1110 {
1111 Hit = TRUE;
1112 }
1113 _SEH2_END
1114
1115 if (Hit)
1116 {
1117 // We don't die, we continue on with a allocated safe pointer to kernel
1118 // space.....
1119 DPRINT1("StretchDIBits fail to read BitMapInfo: %p or Bits: %p & Size: %u\n",
1120 pConvertedInfo, lpBits, cjBmpScanSize);
1121 }
1122 DPRINT("StretchDIBits Allocate Bits %u!!!\n", cjBmpScanSize);
1123 }
1124 }
1125
1126 if (!GdiGetHandleUserData(hdc, GDI_OBJECT_TYPE_DC, (PVOID) & pDc_Attr))
1127 {
1128 DPRINT1("StretchDIBits called on invalid DC %p (not owned?)\n", hdc);
1130 LinesCopied = 0;
1131 goto Exit;
1132 }
1133 /*
1134 if ( !pDc_Attr ||
1135 iUsage == DIB_PAL_COLORS ||
1136 ((pConvertedInfo->bmiHeader.biSize >= sizeof(BITMAPINFOHEADER)) &&
1137 (pConvertedInfo->bmiHeader.biCompression == BI_JPEG ||
1138 pConvertedInfo->bmiHeader.biCompression == BI_PNG )) )*/
1139 {
1140 LinesCopied = NtGdiStretchDIBitsInternal( hdc,
1141 XDest,
1142 YDest,
1143 nDestWidth,
1144 nDestHeight,
1145 XSrc,
1146 YSrc,
1147 nSrcWidth,
1148 nSrcHeight,
1149 pvSafeBits,
1150 pConvertedInfo,
1151 (DWORD) iUsage,
1152 dwRop,
1153 ConvertedInfoSize,
1154 cjBmpScanSize,
1155 NULL );
1156 }
1157Exit:
1158 if (pvSafeBits)
1159 RtlFreeHeap(RtlGetProcessHeap(), 0, pvSafeBits);
1160 if (lpBitsInfo != pConvertedInfo)
1161 RtlFreeHeap(RtlGetProcessHeap(), 0, pConvertedInfo);
1162
1163 return LinesCopied;
1164}
HDC WINAPI GdiConvertAndCheckDC(HDC hdc)
Definition: dc.c:403
__kernel_entry 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_reads_bytes_opt_(cjMaxBits) LPBYTE pjInit, _In_ LPBITMAPINFO pbmi, _In_ DWORD dwUsage, _In_ DWORD dwRop4, _In_ UINT cjMaxInfo, _In_ UINT cjMaxBits, _In_opt_ HANDLE hcmXform)
_In_ HBITMAP _In_ UINT _In_ UINT _Inout_ LPBITMAPINFO _In_ UINT iUsage
Definition: ntgdi.h:2781
int WINAPI StretchDIBits(_In_ HDC, _In_ int, _In_ int, _In_ int, _In_ int, _In_ int, _In_ int, _In_ int, _In_ int, _In_opt_ const VOID *, _In_ const BITMAPINFO *, _In_ UINT, _In_ DWORD)

Variable Documentation

◆ gajBitsPerFormat

UCHAR gajBitsPerFormat[11]
Initial value:
=
{
0,
1,
4,
8,
16,
24,
32,
4,
8,
0,
0,
}

Definition at line 39 of file bitmap.c.

Referenced by SetDIBitsToDevice().