Author: jgardou Date: Tue Mar 1 01:03:58 2011 New Revision: 50941
URL: http://svn.reactos.org/svn/reactos?rev=50941&view=rev Log: [WIN32K] - Raster operations in user mode are on higher bytes, whereas they are on lower bytes for drivers. Try to clarify this situation. - Add sanity check about what was said previously. - Implement masking in EngBitBlt - Rewrite NtGdiMaskBlt accordingly - Realize the palette when selecting it into a device DC. - When applying raster operation, do so only on 24 bits, we don't support alpha channel in win32k This fixes VLC pink icons, Timo's MaskBlt tests and probably a lot of other things. [SHELL32] - Use correct (?) raster operations for drawing sjortcuts. Also note that now NtGdiMaskBlt locks the device contexts : this should avoid some race conditions, such as icons drawn on top of windows and the like. Win32k sucks less. So does reactos. Dedicated to Timo. Sleep well, mate.
Modified: trunk/reactos/dll/win32/shell32/iconcache.c trunk/reactos/subsystems/win32/win32k/dib/dib.c trunk/reactos/subsystems/win32/win32k/dib/dib.h trunk/reactos/subsystems/win32/win32k/dib/dib1bpp.c trunk/reactos/subsystems/win32/win32k/dib/stretchblt.c trunk/reactos/subsystems/win32/win32k/eng/bitblt.c trunk/reactos/subsystems/win32/win32k/eng/copybits.c trunk/reactos/subsystems/win32/win32k/eng/mouse.c trunk/reactos/subsystems/win32/win32k/eng/stretchblt.c trunk/reactos/subsystems/win32/win32k/include/color.h trunk/reactos/subsystems/win32/win32k/include/inteng.h trunk/reactos/subsystems/win32/win32k/ntuser/painting.c trunk/reactos/subsystems/win32/win32k/objects/bitblt.c trunk/reactos/subsystems/win32/win32k/objects/dcobjs.c trunk/reactos/subsystems/win32/win32k/objects/dibobj.c trunk/reactos/subsystems/win32/win32k/objects/drawing.c trunk/reactos/subsystems/win32/win32k/objects/fillshap.c trunk/reactos/subsystems/win32/win32k/objects/freetype.c trunk/reactos/subsystems/win32/win32k/objects/palette.c trunk/reactos/subsystems/win32/win32k/objects/polyfill.c
Modified: trunk/reactos/dll/win32/shell32/iconcache.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/dll/win32/shell32/iconcache... ============================================================================== --- trunk/reactos/dll/win32/shell32/iconcache.c [iso-8859-1] (original) +++ trunk/reactos/dll/win32/shell32/iconcache.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -180,8 +180,8 @@ if (NULL == SelectObject(ShortcutDC, ShortcutIconInfo.hbmColor)) goto fail; if (!MaskBlt(TargetDC, 0, SourceBitmapInfo.bmHeight - ShortcutBitmapInfo.bmHeight, ShortcutBitmapInfo.bmWidth, ShortcutBitmapInfo.bmHeight, - ShortcutDC, 0, 0, ShortcutIconInfo.hbmMask, 0, 0, - MAKEROP4(SRCCOPY, 0xAA0000))) + ShortcutDC, 0, 0, ShortcutIconInfo.hbmMask, 0, 0, + MAKEROP4(0xAA0000, SRCCOPY))) { goto fail; }
Modified: trunk/reactos/subsystems/win32/win32k/dib/dib.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/dib... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/dib/dib.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/dib/dib.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -87,11 +87,12 @@ } };
+ ULONG DIB_DoRop(ULONG Rop, ULONG Dest, ULONG Source, ULONG Pattern) { ULONG ResultNibble; - ULONG Result; + ULONG Result = 0; ULONG i; static const ULONG ExpandDest[16] = { @@ -151,31 +152,34 @@ 0xF0F0F0F0 /* 1111 */, };
- /* Optimized code for the various named rop codes. */ - switch (Rop) - { - case ROP3_TO_ROP4(BLACKNESS): return(0); - case ROP3_TO_ROP4(NOTSRCERASE): return(~(Dest | Source)); - case ROP3_TO_ROP4(NOTSRCCOPY): return(~Source); - case ROP3_TO_ROP4(SRCERASE): return((~Dest) & Source); - case ROP3_TO_ROP4(DSTINVERT): return(~Dest); - case ROP3_TO_ROP4(PATINVERT): return(Dest ^ Pattern); - case ROP3_TO_ROP4(SRCINVERT): return(Dest ^ Source); - case ROP3_TO_ROP4(SRCAND): return(Dest & Source); - case ROP3_TO_ROP4(MERGEPAINT): return(Dest | (~Source)); - case ROP3_TO_ROP4(SRCPAINT): return(Dest | Source); - case ROP3_TO_ROP4(MERGECOPY): return(Source & Pattern); - case ROP3_TO_ROP4(SRCCOPY): return(Source); - case ROP3_TO_ROP4(PATCOPY): return(Pattern); - case ROP3_TO_ROP4(PATPAINT): return(Dest | (~Source) | Pattern); - case ROP3_TO_ROP4(WHITENESS): return(0xFFFFFFFF); + Rop &=0xFF; + switch(Rop) + { + + /* Optimized code for the various named rop codes. */ + case R3_OPINDEX_NOOP: return(Dest); + case R3_OPINDEX_BLACKNESS: return(0); + case R3_OPINDEX_NOTSRCERASE: return(~(Dest | Source)); + case R3_OPINDEX_NOTSRCCOPY: return(~Source); + case R3_OPINDEX_SRCERASE: return((~Dest) & Source); + case R3_OPINDEX_DSTINVERT: return(~Dest); + case R3_OPINDEX_PATINVERT: return(Dest ^ Pattern); + case R3_OPINDEX_SRCINVERT: return(Dest ^ Source); + case R3_OPINDEX_SRCAND: return(Dest & Source); + case R3_OPINDEX_MERGEPAINT: return(Dest | (~Source)); + case R3_OPINDEX_SRCPAINT: return(Dest | Source); + case R3_OPINDEX_MERGECOPY: return(Source & Pattern); + case R3_OPINDEX_SRCCOPY: return(Source); + case R3_OPINDEX_PATCOPY: return(Pattern); + case R3_OPINDEX_PATPAINT: return(Dest | (~Source) | Pattern); + case R3_OPINDEX_WHITENESS: return(0xFFFFFFFF); } + /* Expand the ROP operation to all four bytes */ - Rop &= 0xFF; Rop |= (Rop << 24) | (Rop << 16) | (Rop << 8); /* Do the operation on four bits simultaneously. */ Result = 0; - for (i = 0; i < 8; i++) + for (i = 0; i < 6; i++) { ResultNibble = Rop & ExpandDest[Dest & 0xF] & ExpandSource[Source & 0xF] & ExpandPattern[Pattern & 0xF]; Result |= (((ResultNibble & 0xFF000000) ? 0x8 : 0x0) | ((ResultNibble & 0x00FF0000) ? 0x4 : 0x0) |
Modified: trunk/reactos/subsystems/win32/win32k/dib/dib.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/dib... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/dib/dib.h [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/dib/dib.h [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -31,7 +31,7 @@ POINTL SourcePoint; BRUSHOBJ *Brush; POINTL BrushOrigin; - ULONG Rop4; + ROP4 Rop4; } BLTINFO, *PBLTINFO;
typedef VOID (*PFN_DIB_PutPixel)(SURFOBJ*,LONG,LONG,ULONG);
Modified: trunk/reactos/subsystems/win32/win32k/dib/dib1bpp.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/dib... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/dib/dib1bpp.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/dib/dib1bpp.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -380,7 +380,7 @@ Pattern |= (DIB_GetSourceIndex(PatternObj, (X + BrushOrigin.x + k) % PatternWidth, PatternY) << (31 - k)); }
- Dest = DIB_DoRop(Rop4, Dest, Source, Pattern); + Dest = DIB_DoRop(BltInfo->Rop4, Dest, Source, Pattern); Dest &= ~((1 << (31 - NoBits)) - 1); Dest |= *((PBYTE)DestBits) & ((1 << (31 - NoBits)) - 1);
Modified: trunk/reactos/subsystems/win32/win32k/dib/stretchblt.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/dib... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/dib/stretchblt.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/dib/stretchblt.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -42,6 +42,8 @@ PFN_DIB_GetPixel fnMask_GetPixel = NULL;
LONG PatternX = 0, PatternY = 0; + + ASSERT(IS_VALID_ROP4(ROP));
BOOL UsesSource = ROP4_USES_SOURCE(ROP); BOOL UsesPattern = ROP4_USES_PATTERN(ROP); @@ -122,7 +124,7 @@ { sx = SourceRect->left+(DesX - DestRect->left) * SrcWidth / DstWidth; if (sx < 0 || sy < 0 || - MaskSurf->sizlBitmap.cx < sx || MaskSurf->sizlBitmap.cy < sy || + MaskSurf->sizlBitmap.cx < sx || MaskSurf->sizlBitmap.cy < sy || fnMask_GetPixel(MaskSurf, sx, sy) != 0) { CanDraw = FALSE; @@ -137,10 +139,10 @@ { Source = XLATEOBJ_iXlate(ColorTranslation, fnSource_GetPixel(SourceSurf, sx, sy)); } - else + else { Source = 0; - CanDraw = (ROP3_TO_ROP4(SRCCOPY) != ROP); + CanDraw = ((ROP & 0xFF) != R3_OPINDEX_SRCCOPY); } }
Modified: trunk/reactos/subsystems/win32/win32k/eng/bitblt.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/eng... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/eng/bitblt.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/eng/bitblt.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -27,11 +27,11 @@
static BOOLEAN APIENTRY BltMask(SURFOBJ* psoDest, - SURFOBJ* psoSource, // unused + SURFOBJ* psoSource, SURFOBJ* psoMask, - XLATEOBJ* ColorTranslation, // unused + XLATEOBJ* ColorTranslation, RECTL* prclDest, - POINTL* pptlSource, // unused + POINTL* pptlSource, POINTL* pptlMask, BRUSHOBJ* pbo, POINTL* pptlBrush, @@ -46,19 +46,21 @@ PSURFACE psurfPattern; ULONG PatternWidth = 0, PatternHeight = 0; LONG PatternX0 = 0, PatternX = 0, PatternY = 0; + LONG SrcX = 0, SrcY = 0; PFN_DIB_PutPixel fnDest_PutPixel = NULL; - PFN_DIB_GetPixel fnPattern_GetPixel = NULL; - ULONG Pattern = 0; + PFN_DIB_GetPixel fnPattern_GetPixel = NULL, fnSrc_GetPixel = NULL, fnDest_GetPixel; + ULONG Pattern = 0, Source = 0, Dest = 0; HBITMAP hbmPattern; - - ASSERT(psoSource == NULL); - ASSERT(pptlSource == NULL); - - if (psoMask == NULL) - { - return FALSE; - } - + DWORD fgndRop, bkgndRop; + + ASSERT(IS_VALID_ROP4(Rop4)); + + fgndRop = ROP4_FGND(Rop4); + bkgndRop = ROP4_BKGND(Rop4); + + //DPRINT1("Rop4 : 0x%08x\n", Rop4); + + /* Determine pattern */ if (pbo && pbo->iSolidColor == 0xFFFFFFFF) { pebo = CONTAINING_RECORD(pbo, EBRUSHOBJ, BrushObject); @@ -80,6 +82,18 @@ fjMaskBit0 = 0x80 >> (pptlMask->x & 0x07);
fnDest_PutPixel = DibFunctionsForBitmapFormat[psoDest->iBitmapFormat].DIB_PutPixel; + fnDest_GetPixel = DibFunctionsForBitmapFormat[psoDest->iBitmapFormat].DIB_GetPixel; + + /* Do we have a source */ + if(psoSource) + { + /* Sanity check */ + ASSERT(ROP4_USES_SOURCE(Rop4)); + fnSrc_GetPixel = DibFunctionsForBitmapFormat[psoSource->iBitmapFormat].DIB_GetPixel; + SrcY = pptlSource->y; + SrcX = pptlSource->x; + } + if (psurfPattern) { PatternY = (prclDest->top - pptlBrush->y) % PatternHeight; @@ -92,48 +106,64 @@ { PatternX0 += PatternWidth; } - - for (y = prclDest->top; y < prclDest->bottom; y++) - { - pjMskCurrent = pjMskLine; - fjMaskBit = fjMaskBit0; - PatternX = PatternX0; - - for (x = prclDest->left; x < prclDest->right; x++) + PatternX = PatternX0; + } + else + { + Pattern = pbo ? pbo->iSolidColor : 0; + } + + for (y = prclDest->top; y < prclDest->bottom; y++) + { + pjMskCurrent = pjMskLine; + fjMaskBit = fjMaskBit0; + + for (x = prclDest->left; x < prclDest->right; x++) + { + Rop4 = (*pjMskCurrent & fjMaskBit) ? fgndRop : bkgndRop; + + if(psurfPattern) { - if (*pjMskCurrent & fjMaskBit) - { - fnDest_PutPixel(psoDest, x, y, - fnPattern_GetPixel(psoPattern, PatternX, PatternY)); - } - fjMaskBit = _rotr8(fjMaskBit, 1); - pjMskCurrent += (fjMaskBit >> 7); + if(ROP4_USES_PATTERN(Rop4)) + Pattern = fnPattern_GetPixel(psoPattern, PatternX, PatternY); PatternX++; PatternX %= PatternWidth; } - pjMskLine += psoMask->lDelta; + + if(psoSource) + { + if(ROP4_USES_SOURCE(Rop4)) + { + Source = XLATEOBJ_iXlate(ColorTranslation, + fnSrc_GetPixel(psoSource, SrcX, SrcY)); + } + SrcX++; + } + + if(ROP4_USES_DEST(Rop4)) + Dest = fnDest_GetPixel(psoDest, x, y); + + fnDest_PutPixel(psoDest, + x, + y, + DIB_DoRop(Rop4, + Dest, + Source, + Pattern)); + fjMaskBit = _rotr8(fjMaskBit, 1); + pjMskCurrent += (fjMaskBit >> 7); + } + pjMskLine += psoMask->lDelta; + if(psurfPattern) + { PatternY++; PatternY %= PatternHeight; - } - } - else - { - Pattern = pbo ? pbo->iSolidColor : 0; - for (y = prclDest->top; y < prclDest->bottom; y++) - { - pjMskCurrent = pjMskLine; - fjMaskBit = fjMaskBit0; - - for (x = prclDest->left; x < prclDest->right; x++) - { - if (*pjMskCurrent & fjMaskBit) - { - fnDest_PutPixel(psoDest, x, y, Pattern); - } - fjMaskBit = _rotr8(fjMaskBit, 1); - pjMskCurrent += (fjMaskBit >> 7); - } - pjMskLine += psoMask->lDelta; + PatternX = PatternX0; + } + if(psoSource) + { + SrcY++; + SrcX = pptlSource->x; } }
@@ -153,7 +183,7 @@ POINTL* MaskPoint, BRUSHOBJ* pbo, POINTL* BrushPoint, - ROP4 Rop4) + DWORD Rop4) { // These functions are assigned if we're working with a DIB // The assigned functions depend on the bitsPerPixel of the DIB @@ -188,7 +218,7 @@ BltInfo.DestRect = *OutputRect; BltInfo.SourcePoint = *InputPoint;
- if (ROP3_TO_ROP4(SRCCOPY) == Rop4) + if ((Rop4 & 0xFF) == R3_OPINDEX_SRCCOPY) return DibFunctionsForBitmapFormat[OutputObj->iBitmapFormat].DIB_BitBltSrcCopy(&BltInfo);
BltInfo.Brush = pbo; @@ -244,7 +274,7 @@ IN POINTL *pptlMask, IN BRUSHOBJ *pbo, IN POINTL *pptlBrush, - IN ROP4 rop4 ) + IN ROP4 Rop4) { RECTL rclTrg; POINTL ptlSrc; @@ -272,7 +302,7 @@ } _SEH2_END;
- return EngBitBlt(psoTrg, psoSrc, psoMask, pco, pxlo, &rclTrg, &ptlSrc, &ptlMask, pbo, &ptlBrush, rop4); + return EngBitBlt(psoTrg, psoSrc, psoMask, pco, pxlo, &rclTrg, &ptlSrc, &ptlMask, pbo, &ptlBrush, Rop4); }
/* @@ -289,7 +319,7 @@ POINTL *MaskOrigin, BRUSHOBJ *pbo, POINTL *BrushOrigin, - ROP4 rop4) + ROP4 Rop4) { BYTE clippingType; RECTL CombinedRect; @@ -306,15 +336,19 @@ unsigned i; POINTL Pt; ULONG Direction; - BOOL UsesSource; + BOOL UsesSource, UsesMask; POINTL AdjustedBrushOrigin;
- UsesSource = ROP4_USES_SOURCE(rop4); - if (R4_NOOP == rop4) + UsesSource = ROP4_USES_SOURCE(Rop4); + UsesMask = ROP4_USES_MASK(Rop4); + + if (Rop4 == ROP4_NOOP) { /* Copy destination onto itself: nop */ return TRUE; } + + //DPRINT1("Rop4 : 0x%08x\n", Rop4);
OutputRect = *DestRect; if (OutputRect.right < OutputRect.left) @@ -434,11 +468,11 @@ clippingType = ClipRegion->iDComplexity; }
- if (R4_MASK == rop4) + if (UsesMask) { BltRectFunc = BltMask; } - else if (ROP3_TO_ROP4(PATCOPY) == rop4) + else if ((Rop4 & 0xFF) == R3_OPINDEX_PATCOPY) { if (pbo && pbo->iSolidColor == 0xFFFFFFFF) BltRectFunc = CallDibBitBlt; @@ -456,7 +490,7 @@ case DC_TRIVIAL: Ret = (*BltRectFunc)(OutputObj, InputObj, Mask, ColorTranslation, &OutputRect, &InputPoint, MaskOrigin, pbo, - &AdjustedBrushOrigin, rop4); + &AdjustedBrushOrigin, Rop4); break; case DC_RECT: /* Clip the blt to the clip rectangle */ @@ -470,7 +504,7 @@ Pt.y = InputPoint.y + CombinedRect.top - OutputRect.top; Ret = (*BltRectFunc)(OutputObj, InputObj, Mask, ColorTranslation, &CombinedRect, &Pt, MaskOrigin, pbo, - &AdjustedBrushOrigin, rop4); + &AdjustedBrushOrigin, Rop4); } break; case DC_COMPLEX: @@ -511,7 +545,7 @@ Ret = (*BltRectFunc)(OutputObj, InputObj, Mask, ColorTranslation, &CombinedRect, &Pt, MaskOrigin, pbo, &AdjustedBrushOrigin, - rop4) && Ret; + Rop4) && Ret; } } } @@ -534,7 +568,7 @@ POINTL *pptlMask, BRUSHOBJ *pbo, POINTL *pptlBrush, - ROP4 rop4) + ROP4 Rop4) { SURFACE *psurfTrg; SURFACE *psurfSrc = NULL; @@ -550,6 +584,11 @@ rclClipped = *prclTrg; RECTL_vMakeWellOrdered(&rclClipped);
+ //DPRINT1("Rop4 : 0x%08x\n", Rop4); + + /* Sanity check */ + ASSERT(IS_VALID_ROP4(Rop4)); + if (pco) { /* Clip target rect against the bounds of the clipping region */ @@ -564,7 +603,7 @@ pco = NULL; }
- if (ROP4_USES_SOURCE(rop4)) + if (ROP4_USES_SOURCE(Rop4)) { ASSERT(psoSrc); psurfSrc = CONTAINING_RECORD(psoSrc, SURFACE, SurfObj); @@ -614,7 +653,7 @@ pptlMask, pbo, pptlBrush, - rop4); + Rop4);
// FIXME: cleanup temp surface!
@@ -820,7 +859,7 @@ else Ret = BltMask(psoOutput, NULL, psoInput, DestColorTranslation, &OutputRect, NULL, &InputPoint, pbo, &AdjustedBrushOrigin, - R4_MASK); + ROP4_MASK); break; case DC_RECT: // Clip the blt to the clip rectangle @@ -840,7 +879,7 @@ else { Ret = BltMask(psoOutput, NULL, psoInput, DestColorTranslation, - &CombinedRect, NULL, &Pt, pbo, &AdjustedBrushOrigin, R4_MASK); + &CombinedRect, NULL, &Pt, pbo, &AdjustedBrushOrigin, ROP4_MASK); } } break; @@ -889,7 +928,7 @@ Ret = BltMask(psoOutput, NULL, psoInput, DestColorTranslation, &CombinedRect, NULL, &Pt, pbo, &AdjustedBrushOrigin, - R4_MASK) && Ret; + ROP4_MASK) && Ret; } } } @@ -954,7 +993,7 @@ but the VMware driver doesn't hook that call. */ IntEngBitBlt(psoDest, NULL, psoMask, ClipRegion, DestColorTranslation, DestRect, pptlMask, pptlMask, pbo, BrushOrigin, - R4_NOOP); + ROP4_NOOP);
ret = EngMaskBitBlt(psoDest, psoMask, ClipRegion, DestColorTranslation, SourceColorTranslation, &OutputRect, &InputPoint, pbo, BrushOrigin); @@ -962,7 +1001,7 @@ /* Dummy BitBlt to let driver know that something has changed. */ IntEngBitBlt(psoDest, NULL, psoMask, ClipRegion, DestColorTranslation, DestRect, pptlMask, pptlMask, pbo, BrushOrigin, - R4_NOOP); + ROP4_NOOP);
return ret; }
Modified: trunk/reactos/subsystems/win32/win32k/eng/copybits.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/eng... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/eng/copybits.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/eng/copybits.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -92,7 +92,7 @@ // If CopyBits wasn't hooked, BitBlt must be ret = IntEngBitBlt(psoDest, psoSource, NULL, Clip, ColorTranslation, DestRect, SourcePoint, - NULL, NULL, NULL, ROP3_TO_ROP4(SRCCOPY)); + NULL, NULL, NULL, ROP4_FROM_INDEX(R3_OPINDEX_SRCCOPY));
goto cleanup; } @@ -111,7 +111,7 @@ BltInfo.SourceSurface = psoSource; BltInfo.PatternSurface = NULL; BltInfo.XlateSourceToDest = ColorTranslation; - BltInfo.Rop4 = SRCCOPY; + BltInfo.Rop4 = ROP4_FROM_INDEX(R3_OPINDEX_SRCCOPY);
switch (clippingType) {
Modified: trunk/reactos/subsystems/win32/win32k/eng/mouse.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/eng... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/eng/mouse.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/eng/mouse.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -175,7 +175,7 @@ &ptlSave, NULL, NULL, - ROP3_TO_ROP4(SRCCOPY)); + ROP4_FROM_INDEX(R3_OPINDEX_SRCCOPY)); }
VOID @@ -228,7 +228,7 @@ NULL, NULL, NULL, - ROP3_TO_ROP4(SRCCOPY)); + ROP4_FROM_INDEX(R3_OPINDEX_SRCCOPY));
/* Blt the pointer on the screen. */ if (pgp->psurfColor) @@ -243,7 +243,7 @@ NULL, NULL, NULL, - ROP3_TO_ROP4(SRCAND)); + ROP4_FROM_INDEX(R3_OPINDEX_SRCAND));
IntEngBitBlt(psoDest, &pgp->psurfColor->SurfObj, @@ -255,7 +255,7 @@ NULL, NULL, NULL, - ROP3_TO_ROP4(SRCINVERT)); + ROP4_FROM_INDEX(R3_OPINDEX_SRCINVERT)); } else { @@ -269,7 +269,7 @@ NULL, NULL, NULL, - ROP3_TO_ROP4(SRCAND)); + ROP4_FROM_INDEX(R3_OPINDEX_SRCAND));
rclPointer.top += pgp->Size.cy;
@@ -283,7 +283,7 @@ NULL, NULL, NULL, - ROP3_TO_ROP4(SRCINVERT)); + ROP4_FROM_INDEX(R3_OPINDEX_SRCINVERT)); } }
@@ -337,7 +337,7 @@ rectl.bottom = sizel.cy;
/* Calculate lDelta for our surfaces. */ - lDelta = WIDTH_BYTES_ALIGN32(sizel.cx, + lDelta = WIDTH_BYTES_ALIGN32(sizel.cx, BitsPerFormat(pso->iBitmapFormat));
/* Create a bitmap for saving the pixels under the cursor. */
Modified: trunk/reactos/subsystems/win32/win32k/eng/stretchblt.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/eng... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/eng/stretchblt.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/eng/stretchblt.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -104,7 +104,7 @@ IN POINTL *MaskOrigin, IN ULONG Mode, IN BRUSHOBJ *pbo, - IN DWORD ROP4) + IN ROP4 Rop4) { RECTL InputRect; RECTL OutputRect; @@ -116,7 +116,7 @@ PSTRETCHRECTFUNC BltRectFunc; BOOLEAN Ret = TRUE; POINTL AdjustedBrushOrigin; - BOOL UsesSource = ROP4_USES_SOURCE(ROP4); + BOOL UsesSource = ROP4_USES_SOURCE(Rop4);
BYTE clippingType; RECTL ClipRect; @@ -132,6 +132,13 @@ LONG SrcHeight; LONG SrcWidth;
+ if (Rop4 == ROP4_NOOP) + { + /* Copy destination onto itself: nop */ + return TRUE; + } + + /* Determine clipping type */ if (ClipRegion == (CLIPOBJ *) NULL) { @@ -140,12 +147,6 @@ else { clippingType = ClipRegion->iDComplexity; - } - - if (ROP4 == R4_NOOP) - { - /* Copy destination onto itself: nop */ - return TRUE; }
OutputRect = *prclDest; @@ -257,7 +258,7 @@ case DC_TRIVIAL: Ret = (*BltRectFunc)(psoOutput, psoInput, Mask, ColorTranslation, &OutputRect, &InputRect, MaskOrigin, - pbo, &AdjustedBrushOrigin, ROP4); + pbo, &AdjustedBrushOrigin, Rop4); break; case DC_RECT: // Clip the blt to the clip rectangle @@ -278,7 +279,7 @@ MaskOrigin, pbo, &AdjustedBrushOrigin, - ROP4); + Rop4); } break; case DC_COMPLEX: @@ -323,7 +324,7 @@ MaskOrigin, pbo, &AdjustedBrushOrigin, - ROP4); + Rop4); } } } @@ -371,7 +372,7 @@ MaskOrigin, Mode, NULL, - ROP3_TO_ROP4(SRCCOPY)); + ROP4_FROM_INDEX(R3_OPINDEX_SRCCOPY)); }
BOOL APIENTRY @@ -385,7 +386,7 @@ POINTL *pMaskOrigin, BRUSHOBJ *pbo, POINTL *BrushOrigin, - ROP4 ROP) + DWORD Rop4) { BOOLEAN ret; COLORADJUSTMENT ca; @@ -395,13 +396,16 @@ RECTL InputClippedRect; RECTL InputRect; RECTL OutputRect; - BOOL UsesSource = ROP4_USES_SOURCE(ROP); + BOOL UsesSource = ROP4_USES_SOURCE(Rop4); LONG InputClWidth, InputClHeight, InputWidth, InputHeight;
ASSERT(psoDest); psurfDest = CONTAINING_RECORD(psoDest, SURFACE, SurfObj); ASSERT(psurfDest); ASSERT(DestRect); + + /* Sanity check */ + ASSERT(IS_VALID_ROP4(Rop4));
InputClippedRect = *DestRect; if (InputClippedRect.right < InputClippedRect.left) @@ -485,7 +489,7 @@ &MaskOrigin, COLORONCOLOR, pbo, - ROP); + Rop4); }
if (! ret) @@ -502,7 +506,7 @@ &MaskOrigin, COLORONCOLOR, pbo, - ROP); + Rop4); }
return ret;
Modified: trunk/reactos/subsystems/win32/win32k/include/color.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/inc... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/include/color.h [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/include/color.h [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -27,7 +27,7 @@ typedef struct _COLORTRANSFORMOBJ { BASEOBJECT BaseObject; - HANDLE hColorTransform; + HANDLE hColorTransform; } GDICLRXFORM, COLORTRANSFORMOBJ, *PCOLORTRANSFORMOBJ;
extern HCOLORSPACE hStockColorSpace; @@ -36,6 +36,6 @@ COLORREF APIENTRY COLOR_LookupNearestColor (PALETTEENTRY* palPalEntry, INT size, COLORREF color); INT APIENTRY COLOR_PaletteLookupExactIndex (PALETTEENTRY* palPalEntry, INT size, COLORREF col); INT APIENTRY COLOR_PaletteLookupPixel(PALETTEENTRY *palPalEntry, INT size, XLATEOBJ *XlateObj, COLORREF col, BOOL skipReserved); -UINT FASTCALL IntGdiRealizePalette (HDC); +UINT FASTCALL IntGdiRealizePalette (PDC); HCOLORSPACE FASTCALL IntGdiCreateColorSpace(PLOGCOLORSPACEEXW); BOOL FASTCALL IntGdiDeleteColorSpace(HCOLORSPACE);
Modified: trunk/reactos/subsystems/win32/win32k/include/inteng.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/inc... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/include/inteng.h [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/include/inteng.h [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -17,19 +17,40 @@ ULONG Width; } SPAN, *PSPAN;
-#define R3_OPINDEX_SRCCOPY 0xcc -#define R3_OPINDEX_NOOP 0xaa -#define R4_NOOP ((R3_OPINDEX_NOOP << 8) | R3_OPINDEX_NOOP) -#define R4_MASK ((R3_OPINDEX_NOOP << 8) | R3_OPINDEX_SRCCOPY) +#define R3_OPINDEX_NOOP 0xAA + +#define R3_OPINDEX_BLACKNESS 0x00 +#define R3_OPINDEX_NOTSRCERASE 0x11 +#define R3_OPINDEX_NOTSRCCOPY 0x33 +#define R3_OPINDEX_SRCERASE 0x44 +#define R3_OPINDEX_DSTINVERT 0x55 +#define R3_OPINDEX_PATINVERT 0x5A +#define R3_OPINDEX_SRCINVERT 0x66 +#define R3_OPINDEX_SRCAND 0x88 +#define R3_OPINDEX_MERGEPAINT 0xBB +#define R3_OPINDEX_MERGECOPY 0xC0 +#define R3_OPINDEX_SRCCOPY 0xCC +#define R3_OPINDEX_SRCPAINT 0xEE +#define R3_OPINDEX_PATCOPY 0xF0 +#define R3_OPINDEX_PATPAINT 0xFB +#define R3_OPINDEX_WHITENESS 0xFF
#define ROP2_TO_MIX(Rop2) (((Rop2) << 8) | (Rop2)) -#define ROP3_USES_DEST(Rop3) ((((Rop3) & 0xAA0000) >> 1) != ((Rop3) & 0x550000)) -#define ROP4_USES_DEST(Rop4) (((((Rop4) & 0xAA) >> 1) != ((Rop4) & 0x55)) || ((((Rop4) & 0xAA00) >> 1) != ((Rop4) & 0x5500))) -#define ROP3_USES_SOURCE(Rop3) ((((Rop3) & 0xCC0000) >> 2) != ((Rop3) & 0x330000)) -#define ROP4_USES_SOURCE(Rop4) (((((Rop4) & 0xCC) >> 2) != ((Rop4) & 0x33)) || ((((Rop4) & 0xCC00) >> 2) != ((Rop4) & 0x3300))) -#define ROP3_USES_PATTERN(Rop3) ((((Rop3) & 0xF00000) >> 4) != ((Rop3) & 0x0F0000)) + +#define ROP4_FROM_INDEX(index) ((index) | ((index) << 8)) + +#define ROP4_USES_SOURCE(Rop4) (((((Rop4) & 0xCC00) >> 2) != ((Rop4) & 0x3300)) || ((((Rop4) & 0xCC) >> 2) != ((Rop4) & 0x33))) +#define ROP4_USES_MASK(Rop4) (((Rop4) & 0xFF00) != (((Rop4) & 0xff) << 8)) +#define ROP4_USES_DEST(Rop4) (((((Rop4) & 0xAA) >> 1) != ((Rop4) & 0x55)) || ((((Rop4) & 0xAA00) >> 1) != ((Rop4) & 0x5500))) #define ROP4_USES_PATTERN(Rop4) (((((Rop4) & 0xF0) >> 4) != ((Rop4) & 0x0F)) || ((((Rop4) & 0xF000) >> 4) != ((Rop4) & 0x0F00))) -#define ROP3_TO_ROP4(Rop3) ((((Rop3) >> 8) & 0xff00) | (((Rop3) >> 16) & 0x00ff)) + +#define IS_VALID_ROP4(rop) (((rop) & 0xFFFF0000) == 0) + +#define ROP4_FGND(Rop4) ((Rop4) & 0x00FF) +#define ROP4_BKGND(Rop4) (((Rop4) & 0xFF00) >> 8) + +#define ROP4_NOOP (R3_OPINDEX_NOOP | (R3_OPINDEX_NOOP << 8)) +#define ROP4_MASK (R3_OPINDEX_SRCCOPY | (R3_OPINDEX_NOOP << 8))
/* Definitions of IntEngXxx functions */
Modified: trunk/reactos/subsystems/win32/win32k/ntuser/painting.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/ntu... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/ntuser/painting.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/ntuser/painting.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -307,7 +307,7 @@ /* * IntInvalidateWindows * - * Internal function used by IntRedrawWindow, UserRedrawDesktop, + * Internal function used by IntRedrawWindow, UserRedrawDesktop, * co_WinPosSetWindowPos, IntValidateParent, co_UserRedrawWindow. */ VOID FASTCALL @@ -759,7 +759,7 @@ xSrc = 0; ySrc = 0; } - + // TODO: Setup Redirection for Print. return FALSE;
@@ -1951,7 +1951,11 @@ HWND hWnd; DWORD Ret;
- Ret = IntGdiRealizePalette(hdc); + PDC pdc = DC_LockDc(hdc); + if(!pdc) + return 0; + + Ret = IntGdiRealizePalette(pdc); if (Ret) // There was a change. { hWnd = IntWindowFromDC(hdc); @@ -1960,6 +1964,7 @@ UserSendNotifyMessage((HWND)HWND_BROADCAST, WM_PALETTECHANGED, (WPARAM)hWnd, 0); } } + DC_UnlockDc(pdc); return Ret; }
@@ -2065,7 +2070,7 @@ HDC hdcBlt, UINT nFlags) { - PWND Window; + PWND Window; BOOL Ret = FALSE;
UserEnterExclusive(); @@ -2075,7 +2080,7 @@ Window = UserGetWindowObject(hwnd); // TODO: Add Desktop and MessageBox check via FNID's. if ( Window ) - { + { /* Validate flags and check it as a mask for 0 or 1. */ if ( (nFlags & PW_CLIENTONLY) == nFlags) Ret = IntPrintWindow( Window, hdcBlt, nFlags);
Modified: trunk/reactos/subsystems/win32/win32k/objects/bitblt.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/obj... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/objects/bitblt.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/objects/bitblt.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -23,7 +23,11 @@ #define NDEBUG #include <debug.h>
- +#define ROP_USES_SOURCE(Rop) (((((Rop) & 0xCC0000) >> 2) != ((Rop) & 0x330000)) || ((((Rop) & 0xCC000000) >> 2) != ((Rop) & 0x33000000))) +#define ROP_USES_MASK(Rop) (((Rop) & 0xFF000000) != (((Rop) & 0xff0000) << 8)) + +#define FIXUP_ROP(Rop) if(((Rop) & 0xFF000000) == 0) Rop = MAKEROP4((Rop), (Rop)) +#define ROP_TO_ROP4(Rop) ((Rop) >> 16)
BOOL APIENTRY NtGdiAlphaBlend( @@ -169,144 +173,21 @@ IN DWORD crBackColor, IN FLONG fl) { - PDC DCDest; - PDC DCSrc = NULL; - HDC ahDC[2]; - PGDIOBJ apObj[2]; - PDC_ATTR pdcattr = NULL; - SURFACE *BitmapDest, *BitmapSrc = NULL; - RECTL DestRect, SourceRect; - POINTL SourcePoint; - BOOL Status = FALSE; - EXLATEOBJ exlo; - XLATEOBJ *XlateObj = NULL; - BOOL UsesSource = ROP3_USES_SOURCE(ROP); - - DPRINT("Locking DCs\n"); - ahDC[0] = hDCDest; - ahDC[1] = hDCSrc ; - GDIOBJ_LockMultipleObjs(2, ahDC, apObj); - DCDest = apObj[0]; - DCSrc = apObj[1]; - - if (NULL == DCDest) - { - if(DCSrc) GDIOBJ_UnlockObjByPtr(&DCSrc->BaseObject); - DPRINT("Invalid destination dc handle (0x%08x) passed to NtGdiBitBlt\n", hDCDest); - return FALSE; - } - - if (DCDest->dctype == DC_TYPE_INFO) - { - if(DCSrc) GDIOBJ_UnlockObjByPtr(&DCSrc->BaseObject); - GDIOBJ_UnlockObjByPtr(&DCDest->BaseObject); - /* Yes, Windows really returns TRUE in this case */ - return TRUE; - } - - if (UsesSource) - { - if (NULL == DCSrc) - { - GDIOBJ_UnlockObjByPtr(&DCDest->BaseObject); - DPRINT("Invalid source dc handle (0x%08x) passed to NtGdiBitBlt\n", hDCSrc); - return FALSE; - } - if (DCSrc->dctype == DC_TYPE_INFO) - { - GDIOBJ_UnlockObjByPtr(&DCDest->BaseObject); - GDIOBJ_UnlockObjByPtr(&DCSrc->BaseObject); - /* Yes, Windows really returns TRUE in this case */ - return TRUE; - } - } - else if(DCSrc) - { - DPRINT1("Getting a valid Source handle without using source!!!\n"); - GDIOBJ_UnlockObjByPtr(&DCSrc->BaseObject); - DCSrc = NULL ; - } - - pdcattr = DCDest->pdcattr; - - DestRect.left = XDest; - DestRect.top = YDest; - DestRect.right = XDest+Width; - DestRect.bottom = YDest+Height; - IntLPtoDP(DCDest, (LPPOINT)&DestRect, 2); - - DestRect.left += DCDest->ptlDCOrig.x; - DestRect.top += DCDest->ptlDCOrig.y; - DestRect.right += DCDest->ptlDCOrig.x; - DestRect.bottom += DCDest->ptlDCOrig.y; - - SourcePoint.x = XSrc; - SourcePoint.y = YSrc; - - if (UsesSource) - { - IntLPtoDP(DCSrc, (LPPOINT)&SourcePoint, 1); - - SourcePoint.x += DCSrc->ptlDCOrig.x; - SourcePoint.y += DCSrc->ptlDCOrig.y; - /* Calculate Source Rect */ - SourceRect.left = SourcePoint.x; - SourceRect.top = SourcePoint.y; - SourceRect.right = SourcePoint.x + DestRect.right - DestRect.left; - SourceRect.bottom = SourcePoint.y + DestRect.bottom - DestRect.top ; - } - - /* Prepare blit */ - DC_vPrepareDCsForBlit(DCDest, DestRect, DCSrc, SourceRect); - - if (pdcattr->ulDirty_ & (DIRTY_FILL | DC_BRUSH_DIRTY)) - DC_vUpdateFillBrush(DCDest); - - /* Determine surfaces to be used in the bitblt */ - BitmapDest = DCDest->dclevel.pSurface; - if (!BitmapDest) - goto cleanup; - - if (UsesSource) - { - { - BitmapSrc = DCSrc->dclevel.pSurface; - if (!BitmapSrc) - goto cleanup; - } - } - - /* Create the XLATEOBJ. */ - if (UsesSource) - { - EXLATEOBJ_vInitXlateFromDCs(&exlo, DCSrc, DCDest); - XlateObj = &exlo.xlo; - } - - /* Perform the bitblt operation */ - Status = IntEngBitBlt(&BitmapDest->SurfObj, - BitmapSrc ? &BitmapSrc->SurfObj : NULL, - NULL, - DCDest->rosdc.CombinedClip, - XlateObj, - &DestRect, - &SourcePoint, - NULL, - &DCDest->eboFill.BrushObject, - &DCDest->dclevel.pbrFill->ptOrigin, - ROP3_TO_ROP4(ROP)); - - if (UsesSource) - EXLATEOBJ_vCleanup(&exlo); -cleanup: - DC_vFinishBlit(DCDest, DCSrc); - if (UsesSource) - { - GDIOBJ_UnlockObjByPtr(&DCSrc->BaseObject); - } - GDIOBJ_UnlockObjByPtr(&DCDest->BaseObject); - - return Status; + /* Forward to NtGdiMaskBlt */ + // TODO : what's fl for? + return NtGdiMaskBlt(hDCDest, + XDest, + YDest, + Width, + Height, + hDCSrc, + XSrc, + YSrc, + NULL, + 0, + 0, + ROP, + crBackColor); }
BOOL APIENTRY @@ -413,86 +294,6 @@
return Ret; } - -/*********************************************************************** -* MaskBlt -* Ported from WINE by sedwards 11-4-03 -* -* Someone thought it would be faster to do it here and then switch back -* to GDI32. I dunno. Write a test and let me know. -* A. It should be in here! -*/ - -static const DWORD ROP3Table[256] = -{ - 0x000042, 0x010289, 0x020C89, 0x0300AA, 0x040C88, 0x0500A9, 0x060865, 0x0702C5, - 0x080F08, 0x090245, 0x0A0329, 0x0B0B2A, 0x0C0324, 0x0D0B25, 0x0E08A5, 0x0F0001, - 0x100C85, 0x1100A6, 0x120868, 0x1302C8, 0x140869, 0x1502C9, 0x165CCA, 0x171D54, - 0x180D59, 0x191CC8, 0x1A06C5, 0x1B0768, 0x1C06CA, 0x1D0766, 0x1E01A5, 0x1F0385, - 0x200F09, 0x210248, 0x220326, 0x230B24, 0x240D55, 0x251CC5, 0x2606C8, 0x271868, - 0x280369, 0x2916CA, 0x2A0CC9, 0x2B1D58, 0x2C0784, 0x2D060A, 0x2E064A, 0x2F0E2A, - 0x30032A, 0x310B28, 0x320688, 0x330008, 0x3406C4, 0x351864, 0x3601A8, 0x370388, - 0x38078A, 0x390604, 0x3A0644, 0x3B0E24, 0x3C004A, 0x3D18A4, 0x3E1B24, 0x3F00EA, - 0x400F0A, 0x410249, 0x420D5D, 0x431CC4, 0x440328, 0x450B29, 0x4606C6, 0x47076A, - 0x480368, 0x4916C5, 0x4A0789, 0x4B0605, 0x4C0CC8, 0x4D1954, 0x4E0645, 0x4F0E25, - 0x500325, 0x510B26, 0x5206C9, 0x530764, 0x5408A9, 0x550009, 0x5601A9, 0x570389, - 0x580785, 0x590609, 0x5A0049, 0x5B18A9, 0x5C0649, 0x5D0E29, 0x5E1B29, 0x5F00E9, - 0x600365, 0x6116C6, 0x620786, 0x630608, 0x640788, 0x650606, 0x660046, 0x6718A8, - 0x6858A6, 0x690145, 0x6A01E9, 0x6B178A, 0x6C01E8, 0x6D1785, 0x6E1E28, 0x6F0C65, - 0x700CC5, 0x711D5C, 0x720648, 0x730E28, 0x740646, 0x750E26, 0x761B28, 0x7700E6, - 0x7801E5, 0x791786, 0x7A1E29, 0x7B0C68, 0x7C1E24, 0x7D0C69, 0x7E0955, 0x7F03C9, - 0x8003E9, 0x810975, 0x820C49, 0x831E04, 0x840C48, 0x851E05, 0x8617A6, 0x8701C5, - 0x8800C6, 0x891B08, 0x8A0E06, 0x8B0666, 0x8C0E08, 0x8D0668, 0x8E1D7C, 0x8F0CE5, - 0x900C45, 0x911E08, 0x9217A9, 0x9301C4, 0x9417AA, 0x9501C9, 0x960169, 0x97588A, - 0x981888, 0x990066, 0x9A0709, 0x9B07A8, 0x9C0704, 0x9D07A6, 0x9E16E6, 0x9F0345, - 0xA000C9, 0xA11B05, 0xA20E09, 0xA30669, 0xA41885, 0xA50065, 0xA60706, 0xA707A5, - 0xA803A9, 0xA90189, 0xAA0029, 0xAB0889, 0xAC0744, 0xAD06E9, 0xAE0B06, 0xAF0229, - 0xB00E05, 0xB10665, 0xB21974, 0xB30CE8, 0xB4070A, 0xB507A9, 0xB616E9, 0xB70348, - 0xB8074A, 0xB906E6, 0xBA0B09, 0xBB0226, 0xBC1CE4, 0xBD0D7D, 0xBE0269, 0xBF08C9, - 0xC000CA, 0xC11B04, 0xC21884, 0xC3006A, 0xC40E04, 0xC50664, 0xC60708, 0xC707AA, - 0xC803A8, 0xC90184, 0xCA0749, 0xCB06E4, 0xCC0020, 0xCD0888, 0xCE0B08, 0xCF0224, - 0xD00E0A, 0xD1066A, 0xD20705, 0xD307A4, 0xD41D78, 0xD50CE9, 0xD616EA, 0xD70349, - 0xD80745, 0xD906E8, 0xDA1CE9, 0xDB0D75, 0xDC0B04, 0xDD0228, 0xDE0268, 0xDF08C8, - 0xE003A5, 0xE10185, 0xE20746, 0xE306EA, 0xE40748, 0xE506E5, 0xE61CE8, 0xE70D79, - 0xE81D74, 0xE95CE6, 0xEA02E9, 0xEB0849, 0xEC02E8, 0xED0848, 0xEE0086, 0xEF0A08, - 0xF00021, 0xF10885, 0xF20B05, 0xF3022A, 0xF40B0A, 0xF50225, 0xF60265, 0xF708C5, - 0xF802E5, 0xF90845, 0xFA0089, 0xFB0A09, 0xFC008A, 0xFD0A0A, 0xFE02A9, 0xFF0062, -}; - -static __inline BYTE -SwapROP3_SrcDst(BYTE bRop3) -{ - return (bRop3 & 0x99) | ((bRop3 & 0x22) << 1) | ((bRop3 & 0x44) >> 1); -} - -#define FRGND_ROP3(ROP4) ((ROP4) & 0x00FFFFFF) -#define BKGND_ROP3(ROP4) (ROP3Table[(SwapROP3_SrcDst((ROP4)>>24)) & 0xFF]) -#define DSTCOPY 0x00AA0029 -#define DSTERASE 0x00220326 /* dest = dest & (~src) : DSna */ - -/* NOTE: An alternative algorithm could use a pattern brush, created from - * the mask bitmap and then use raster operation 0xCA to combine the fore - * and background bitmaps. In this case erasing the bits beforehand would be - * unneccessary. On the other hand the Operation does not provide an optimized - * version in the DIB code, while SRCAND and SRCPAINT do. - * A fully correct implementation would call Eng/DrvBitBlt, but our - * EngBitBlt completely ignores the mask surface. - * - * Msk Fg Bk => x - * P S D DPSDxax - * ------------------------------------------ - * 0 0 0 0 0000xax = 000ax = 00x = 0 - * 0 0 1 1 1001xax = 101ax = 10x = 1 - * 0 1 0 0 0010xax = 001ax = 00x = 0 - * 0 1 1 1 1011xax = 100ax = 10x = 1 - * 1 0 0 0 0100xax = 010ax = 00x = 0 - * 1 0 1 0 1101xax = 111ax = 11x = 0 - * 1 1 0 1 0110xax = 011ax = 01x = 1 - * 1 1 1 1 1111xax = 110ax = 10x = 1 - * - * Operation index = 11001010 = 0xCA = PSaDPnao = DPSDxax - * ^ no, this is not random letters, its reverse Polish notation - */
BOOL APIENTRY NtGdiMaskBlt( @@ -510,97 +311,188 @@ DWORD dwRop, IN DWORD crBackColor) { - HBITMAP hbmFore, hbmBack; - HDC hdcMask, hdcFore, hdcBack; - PDC pdc; - HBRUSH hbr; - COLORREF crFore, crBack; - - if (!hbmMask) - return NtGdiBitBlt(hdcDest, - nXDest, - nYDest, - nWidth, - nHeight, - hdcSrc, - nXSrc, - nYSrc, - FRGND_ROP3(dwRop), - crBackColor, - 0); - - /* Lock the dest DC */ - pdc = DC_LockDc(hdcDest); - if (!pdc) return FALSE; - - /* Get brush and colors from dest dc */ - hbr = pdc->pdcattr->hbrush; - crFore = pdc->pdcattr->crForegroundClr; - crBack = pdc->pdcattr->crBackgroundClr; - - /* Unlock the DC */ - DC_UnlockDc(pdc); - - /* 1. Create mask bitmap's dc */ - hdcMask = NtGdiCreateCompatibleDC(hdcDest); - NtGdiSelectBitmap(hdcMask, hbmMask); - - /* 2. Create masked Background bitmap */ - - /* 2.1 Create bitmap */ - hdcBack = NtGdiCreateCompatibleDC(hdcDest); - hbmBack = NtGdiCreateCompatibleBitmap(hdcDest, nWidth, nHeight); - NtGdiSelectBitmap(hdcBack, hbmBack); - - /* 2.2 Copy source bitmap */ - NtGdiSelectBrush(hdcBack, hbr); - IntGdiSetBkColor(hdcBack, crBack); - IntGdiSetTextColor(hdcBack, crFore); - NtGdiBitBlt(hdcBack, 0, 0, nWidth, nHeight, hdcSrc, nXSrc, nYSrc, SRCCOPY, 0, 0); - - /* 2.3 Do the background rop */ - NtGdiBitBlt(hdcBack, 0, 0, nWidth, nHeight, hdcDest, nXDest, nYDest, BKGND_ROP3(dwRop), 0, 0); - - /* 2.4 Erase the foreground pixels */ - IntGdiSetBkColor(hdcBack, RGB(0xFF, 0xFF, 0xFF)); - IntGdiSetTextColor(hdcBack, RGB(0, 0, 0)); - NtGdiBitBlt(hdcBack, 0, 0, nWidth, nHeight, hdcMask, xMask, yMask, SRCAND, 0, 0); - - /* 3. Create masked Foreground bitmap */ - - /* 3.1 Create bitmap */ - hdcFore = NtGdiCreateCompatibleDC(hdcDest); - hbmFore = NtGdiCreateCompatibleBitmap(hdcDest, nWidth, nHeight); - NtGdiSelectBitmap(hdcFore, hbmFore); - - /* 3.2 Copy the dest bitmap */ - NtGdiSelectBrush(hdcFore, hbr); - IntGdiSetBkColor(hdcFore, crBack); - IntGdiSetTextColor(hdcFore, crFore); - NtGdiBitBlt(hdcFore, 0, 0, nWidth, nHeight, hdcDest, nXDest, nYDest, SRCCOPY, 0, 0); - - /* 2.3 Do the foreground rop */ - NtGdiBitBlt(hdcFore, 0, 0, nWidth, nHeight, hdcSrc, nXSrc, nYSrc, FRGND_ROP3(dwRop), 0,0); - - /* 2.4 Erase the background pixels */ - IntGdiSetBkColor(hdcFore, RGB(0, 0, 0)); - IntGdiSetTextColor(hdcFore, RGB(0xFF, 0xFF, 0xFF)); - NtGdiBitBlt(hdcFore, 0, 0, nWidth, nHeight, hdcMask, xMask, yMask, SRCAND, 0, 0); - - /* 3. Combine the fore and background into the background bitmap */ - NtGdiBitBlt(hdcBack, 0, 0, nWidth, nHeight, hdcFore, 0, 0, SRCPAINT, 0, 0); - - /* 4. Copy the result to hdcDest */ - NtGdiBitBlt(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcBack, 0, 0, SRCCOPY, 0, 0); - - /* 5. delete all temp objects */ - NtGdiDeleteObjectApp(hdcBack); - NtGdiDeleteObjectApp(hdcFore); - NtGdiDeleteObjectApp(hdcMask); - GreDeleteObject(hbmFore); - GreDeleteObject(hbmBack); - - return TRUE; + PDC DCDest; + PDC DCSrc = NULL; + HDC ahDC[2]; + PGDIOBJ apObj[2]; + PDC_ATTR pdcattr = NULL; + SURFACE *BitmapDest, *BitmapSrc = NULL, *psurfMask = NULL; + RECTL DestRect, SourceRect; + POINTL SourcePoint, MaskPoint; + BOOL Status = FALSE; + EXLATEOBJ exlo; + XLATEOBJ *XlateObj = NULL; + BOOL UsesSource = ROP_USES_SOURCE(dwRop); + BOOL UsesMask; + + FIXUP_ROP(dwRop); + + UsesMask = ROP_USES_MASK(dwRop); + + //DPRINT1("dwRop : 0x%08x\n", dwRop); + + /* Take care of mask bitmap */ + if(hbmMask) + { + psurfMask = SURFACE_LockSurface(hbmMask); + if(!psurfMask) + { + EngSetLastError(ERROR_INVALID_HANDLE); + return FALSE; + } + } + + if(UsesMask) + { + if(!psurfMask) + { + EngSetLastError(ERROR_INVALID_PARAMETER); + return FALSE; + } + if(gajBitsPerFormat[psurfMask->SurfObj.iBitmapFormat] != 1) + { + EngSetLastError(ERROR_INVALID_PARAMETER); + SURFACE_UnlockSurface(psurfMask); + return FALSE; + } + } + else if(psurfMask) + { + DPRINT1("Getting Mask bitmap without needing it?\n"); + SURFACE_UnlockSurface(psurfMask); + psurfMask = NULL; + } + MaskPoint.x = xMask; + MaskPoint.y = yMask; + + /* Take care of source and destination bitmap */ + DPRINT("Locking DCs\n"); + ahDC[0] = hdcDest; + ahDC[1] = hdcSrc ; + GDIOBJ_LockMultipleObjs(2, ahDC, apObj); + DCDest = apObj[0]; + DCSrc = apObj[1]; + + if (NULL == DCDest) + { + if(DCSrc) DC_UnlockDc(DCSrc); + DPRINT("Invalid destination dc handle (0x%08x) passed to NtGdiBitBlt\n", hdcDest); + return FALSE; + } + + if (DCDest->dctype == DC_TYPE_INFO) + { + if(DCSrc) DC_UnlockDc(DCSrc); + DC_UnlockDc(DCDest); + /* Yes, Windows really returns TRUE in this case */ + return TRUE; + } + + if (UsesSource) + { + if (NULL == DCSrc) + { + DC_UnlockDc(DCDest); + DPRINT("Invalid source dc handle (0x%08x) passed to NtGdiBitBlt\n", hdcSrc); + return FALSE; + } + if (DCSrc->dctype == DC_TYPE_INFO) + { + DC_UnlockDc(DCDest); + DC_UnlockDc(DCSrc); + /* Yes, Windows really returns TRUE in this case */ + return TRUE; + } + } + else if(DCSrc) + { + DPRINT("Getting a valid Source handle without using source!!!\n"); + DC_UnlockDc(DCSrc); + DCSrc = NULL ; + } + + pdcattr = DCDest->pdcattr; + + DestRect.left = nXDest; + DestRect.top = nYDest; + DestRect.right = nXDest + nWidth; + DestRect.bottom = nYDest + nHeight; + IntLPtoDP(DCDest, (LPPOINT)&DestRect, 2); + + DestRect.left += DCDest->ptlDCOrig.x; + DestRect.top += DCDest->ptlDCOrig.y; + DestRect.right += DCDest->ptlDCOrig.x; + DestRect.bottom += DCDest->ptlDCOrig.y; + + SourcePoint.x = nXSrc; + SourcePoint.y = nYSrc; + + if (UsesSource) + { + IntLPtoDP(DCSrc, (LPPOINT)&SourcePoint, 1); + + SourcePoint.x += DCSrc->ptlDCOrig.x; + SourcePoint.y += DCSrc->ptlDCOrig.y; + /* Calculate Source Rect */ + SourceRect.left = SourcePoint.x; + SourceRect.top = SourcePoint.y; + SourceRect.right = SourcePoint.x + DestRect.right - DestRect.left; + SourceRect.bottom = SourcePoint.y + DestRect.bottom - DestRect.top ; + } + + /* Prepare blit */ + DC_vPrepareDCsForBlit(DCDest, DestRect, DCSrc, SourceRect); + + if (pdcattr->ulDirty_ & (DIRTY_FILL | DC_BRUSH_DIRTY)) + DC_vUpdateFillBrush(DCDest); + + /* Determine surfaces to be used in the bitblt */ + BitmapDest = DCDest->dclevel.pSurface; + if (!BitmapDest) + goto cleanup; + + if (UsesSource) + { + { + BitmapSrc = DCSrc->dclevel.pSurface; + if (!BitmapSrc) + goto cleanup; + } + } + + /* Create the XLATEOBJ. */ + if (UsesSource) + { + EXLATEOBJ_vInitXlateFromDCs(&exlo, DCSrc, DCDest); + XlateObj = &exlo.xlo; + } + + + /* Perform the bitblt operation */ + Status = IntEngBitBlt(&BitmapDest->SurfObj, + BitmapSrc ? &BitmapSrc->SurfObj : NULL, + psurfMask ? &psurfMask->SurfObj : NULL, + DCDest->rosdc.CombinedClip, + XlateObj, + &DestRect, + &SourcePoint, + &MaskPoint, + &DCDest->eboFill.BrushObject, + &DCDest->dclevel.pbrFill->ptOrigin, + ROP_TO_ROP4(dwRop)); + + if (UsesSource) + EXLATEOBJ_vCleanup(&exlo); +cleanup: + DC_vFinishBlit(DCDest, DCSrc); + if (UsesSource) + { + DC_UnlockDc(DCSrc); + } + DC_UnlockDc(DCDest); + if(psurfMask) SURFACE_UnlockSurface(psurfMask); + + return Status; }
BOOL @@ -655,7 +547,9 @@ EXLATEOBJ exlo; XLATEOBJ *XlateObj = NULL; POINTL BrushOrigin; - BOOL UsesSource = ROP3_USES_SOURCE(ROP); + BOOL UsesSource = ROP_USES_SOURCE(ROP); + + FIXUP_ROP(ROP);
if (0 == WidthDest || 0 == HeightDest || 0 == WidthSrc || 0 == HeightSrc) { @@ -803,7 +697,7 @@ BitmapMask ? &MaskPoint : NULL, &DCDest->eboFill.BrushObject, &BrushOrigin, - ROP3_TO_ROP4(ROP)); + ROP_TO_ROP4(ROP)); if (UsesSource) { EXLATEOBJ_vCleanup(&exlo); @@ -877,6 +771,8 @@
ASSERT(pbrush);
+ FIXUP_ROP(dwRop); + if (pbrush->flAttrs & GDIBRUSH_IS_NULL) { return TRUE; @@ -934,7 +830,7 @@ NULL, &eboFill.BrushObject, &BrushOrigin, - ROP3_TO_ROP4(dwRop)); + ROP_TO_ROP4(dwRop));
DC_vFinishBlit(pdc, NULL);
@@ -1007,7 +903,7 @@ PDC_ATTR pdcattr; BOOL ret;
- BOOL UsesSource = ROP3_USES_SOURCE(ROP); + BOOL UsesSource = ROP_USES_SOURCE(ROP); if (UsesSource) { /* in this case we call on GdiMaskBlt */
Modified: trunk/reactos/subsystems/win32/win32k/objects/dcobjs.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/obj... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/objects/dcobjs.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/objects/dcobjs.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -177,6 +177,11 @@ /* Mark the brushes invalid */ pdc->pdcattr->ulDirty_ |= DIRTY_FILL | DIRTY_LINE | DIRTY_BACKGROUND | DIRTY_TEXT; + } + + if(pdc->dctype == DCTYPE_MEMORY) + { + IntGdiRealizePalette(pdc); }
PALETTE_ShareUnlockPalette(ppal);
Modified: trunk/reactos/subsystems/win32/win32k/objects/dibobj.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/obj... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/objects/dibobj.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/objects/dibobj.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -531,7 +531,7 @@ NULL, NULL, NULL, - ROP3_TO_ROP4(SRCCOPY)); + ROP4_FROM_INDEX(R3_OPINDEX_SRCCOPY));
/* Cleanup EXLATEOBJ */ EXLATEOBJ_vCleanup(&exlo);
Modified: trunk/reactos/subsystems/win32/win32k/objects/drawing.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/obj... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/objects/drawing.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/objects/drawing.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -1249,7 +1249,7 @@ PBRUSH pbrush, BOOL Pen) { - DWORD ROP = PATCOPY; + DWORD ROP = ROP4_FROM_INDEX(R3_OPINDEX_PATCOPY); RECTL DestRect; SURFACE *psurf; POINTL BrushOrigin; @@ -1291,7 +1291,7 @@ BrushOrigin.y = pbrush->ptOrigin.y;
if (pdcattr->jROP2 == R2_XORPEN) - ROP = PATINVERT; + ROP = ROP4_FROM_INDEX(R3_OPINDEX_PATINVERT);
Ret = IntEngBitBlt( &psurf->SurfObj, @@ -1304,7 +1304,7 @@ NULL, Pen ? &dc->eboLine.BrushObject : &dc->eboFill.BrushObject, &BrushOrigin, - ROP3_TO_ROP4(ROP)); + ROP); }
return (int)Ret;
Modified: trunk/reactos/subsystems/win32/win32k/objects/fillshap.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/obj... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/objects/fillshap.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/objects/fillshap.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -604,7 +604,7 @@ NULL, &dc->eboFill.BrushObject, &BrushOrigin, - ROP3_TO_ROP4(PATCOPY)); + ROP4_FROM_INDEX(R3_OPINDEX_PATCOPY)); } }
Modified: trunk/reactos/subsystems/win32/win32k/objects/freetype.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/obj... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/objects/freetype.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/objects/freetype.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -3269,7 +3269,7 @@ &SourcePoint, &dc->eboBackground.BrushObject, &BrushOrigin, - ROP3_TO_ROP4(PATCOPY)); + ROP4_FROM_INDEX(R3_OPINDEX_PATCOPY)); fuOptions &= ~ETO_OPAQUE; DC_vFinishBlit(dc, NULL); } @@ -3514,7 +3514,7 @@ &SourcePoint, &dc->eboBackground.BrushObject, &BrushOrigin, - ROP3_TO_ROP4(PATCOPY)); + ROP4_FROM_INDEX(R3_OPINDEX_PATCOPY)); MouseSafetyOnDrawEnd(dc->ppdev); BackgroundLeft = DestRect.right;
Modified: trunk/reactos/subsystems/win32/win32k/objects/palette.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/obj... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/objects/palette.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/objects/palette.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -723,18 +723,10 @@
UINT FASTCALL -IntGdiRealizePalette(HDC hDC) +IntGdiRealizePalette(PDC pdc) { UINT i, realize = 0; - PDC pdc; PALETTE *ppalSurf, *ppalDC; - - pdc = DC_LockDc(hDC); - if(!pdc) - { - EngSetLastError(ERROR_INVALID_HANDLE); - return 0; - }
ppalSurf = pdc->dclevel.pSurface->ppal; ppalDC = pdc->dclevel.ppal; @@ -742,7 +734,7 @@ if(!(ppalSurf->flFlags & PAL_INDEXED)) { // FIXME : set error? - goto cleanup; + return 0; }
ASSERT(ppalDC->flFlags & PAL_INDEXED); @@ -755,8 +747,6 @@ InterlockedExchange((LONG*)&ppalSurf->IndexedColors[i], *(LONG*)&ppalDC->IndexedColors[i]); }
-cleanup: - DC_UnlockDc(pdc); return realize; }
@@ -810,11 +800,9 @@ { if (dc->dclevel.hpal == hPal) { - DC_UnlockDc(dc); - IntGdiRealizePalette(hDC); + IntGdiRealizePalette(dc); } - else - DC_UnlockDc(dc); + DC_UnlockDc(dc); } UserReleaseDC(Wnd,hDC, FALSE); }
Modified: trunk/reactos/subsystems/win32/win32k/objects/polyfill.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/obj... ============================================================================== --- trunk/reactos/subsystems/win32/win32k/objects/polyfill.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/win32/win32k/objects/polyfill.c [iso-8859-1] Tue Mar 1 01:03:58 2011 @@ -606,14 +606,14 @@ BRUSHOBJ *BrushObj, CONST PPOINT Points, int Count, - RECTL DestRect, + RECTL DestRect, POINTL *BrushOrigin) { FILL_EDGE_LIST *list = 0; FILL_EDGE *ActiveHead = 0; FILL_EDGE *pLeft, *pRight; int ScanLine; - + //DPRINT("IntFillPolygon\n");
/* Create Edge List. */ @@ -657,11 +657,11 @@ NULL, BrushObj, BrushOrigin, - ROP3_TO_ROP4(PATCOPY)); + ROP4_FROM_INDEX(R3_OPINDEX_PATCOPY)); } pLeft = pRight->pNext; pRight = pLeft ? pLeft->pNext : NULL; - } + } }
/* Free Edge List. If any are left. */