Author: jimtabor
Date: Tue Jul 29 13:11:18 2008
New Revision: 34934
URL:
http://svn.reactos.org/svn/reactos?rev=34934&view=rev
Log:
- Patch by Jeffrey Morlan: Fix bounds checking and change NtGdiDoPalette to use a
temporary kmode buffer. See Bug 3383.
Modified:
trunk/reactos/subsystems/win32/win32k/objects/color.c
Modified: trunk/reactos/subsystems/win32/win32k/objects/color.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/win32k/ob…
==============================================================================
--- trunk/reactos/subsystems/win32/win32k/objects/color.c [iso-8859-1] (original)
+++ trunk/reactos/subsystems/win32/win32k/objects/color.c [iso-8859-1] Tue Jul 29 13:11:18
2008
@@ -436,18 +436,16 @@
{
if (pe != NULL)
{
- UINT CopyEntries;
-
- if (StartIndex + Entries < palGDI->NumColors)
- CopyEntries = StartIndex + Entries;
- else
- CopyEntries = palGDI->NumColors - StartIndex;
+ if (StartIndex >= palGDI->NumColors)
+ Entries = 0;
+ else if (Entries > palGDI->NumColors - StartIndex)
+ Entries = palGDI->NumColors - StartIndex;
memcpy(pe,
palGDI->IndexedColors + StartIndex,
- CopyEntries * sizeof(pe[0]));
-
- Ret = CopyEntries;
+ Entries * sizeof(pe[0]));
+
+ Ret = Entries;
}
else
{
@@ -837,6 +835,7 @@
IN BOOL bInbound)
{
LONG ret;
+ LPVOID pEntries = NULL;
/* FIXME: Handle bInbound correctly */
@@ -846,58 +845,76 @@
return 0;
}
- _SEH_TRY
+ if (pUnsafeEntries)
{
- switch(iFunc)
+ pEntries = ExAllocatePool(PagedPool, cEntries * sizeof(PALETTEENTRY));
+ if (!pEntries)
+ return 0;
+ if (bInbound)
{
- case GdiPalAnimate:
+ _SEH_TRY
+ {
ProbeForRead(pUnsafeEntries, cEntries * sizeof(PALETTEENTRY), 1);
- ret = IntAnimatePalette((HPALETTE)hObj, iStart, cEntries, pUnsafeEntries);
- break;
-
- case GdiPalSetEntries:
- ProbeForRead(pUnsafeEntries, cEntries * sizeof(PALETTEENTRY), 1);
- ret = IntSetPaletteEntries((HPALETTE)hObj, iStart, cEntries, pUnsafeEntries);
- break;
-
- case GdiPalGetEntries:
- if (pUnsafeEntries)
- {
- ProbeForWrite(pUnsafeEntries, cEntries * sizeof(PALETTEENTRY), 1);
- }
- ret = IntGetPaletteEntries((HPALETTE)hObj, iStart, cEntries, pUnsafeEntries);
- break;
-
- case GdiPalGetSystemEntries:
- if (pUnsafeEntries)
- {
- ProbeForWrite(pUnsafeEntries, cEntries * sizeof(PALETTEENTRY), 1);
- }
- ret = IntGetSystemPaletteEntries((HDC)hObj, iStart, cEntries, pUnsafeEntries);
- break;
-
- case GdiPalSetColorTable:
- ProbeForRead(pUnsafeEntries, cEntries * sizeof(PALETTEENTRY), 1);
- ret = IntSetDIBColorTable((HDC)hObj, iStart, cEntries, (RGBQUAD*)pUnsafeEntries);
- break;
-
- case GdiPalGetColorTable:
- if (pUnsafeEntries)
- {
- ProbeForWrite(pUnsafeEntries, cEntries * sizeof(PALETTEENTRY), 1);
- }
- ret = IntGetDIBColorTable((HDC)hObj, iStart, cEntries, (RGBQUAD*)pUnsafeEntries);
- break;
-
- default:
- ret = 0;
+ memcpy(pEntries, pUnsafeEntries, cEntries * sizeof(PALETTEENTRY));
+ }
+ _SEH_HANDLE
+ {
+ ExFreePool(pEntries);
+ _SEH_YIELD(return 0);
+ }
+ _SEH_END
}
}
- _SEH_HANDLE
+
+ ret = 0;
+ switch(iFunc)
{
- ret = 0;
+ case GdiPalAnimate:
+ if (pEntries)
+ ret = IntAnimatePalette((HPALETTE)hObj, iStart, cEntries, pEntries);
+ break;
+
+ case GdiPalSetEntries:
+ if (pEntries)
+ ret = IntSetPaletteEntries((HPALETTE)hObj, iStart, cEntries, pEntries);
+ break;
+
+ case GdiPalGetEntries:
+ ret = IntGetPaletteEntries((HPALETTE)hObj, iStart, cEntries, pEntries);
+ break;
+
+ case GdiPalGetSystemEntries:
+ ret = IntGetSystemPaletteEntries((HDC)hObj, iStart, cEntries, pEntries);
+ break;
+
+ case GdiPalSetColorTable:
+ if (pEntries)
+ ret = IntSetDIBColorTable((HDC)hObj, iStart, cEntries, (RGBQUAD*)pEntries);
+ break;
+
+ case GdiPalGetColorTable:
+ if (pEntries)
+ ret = IntGetDIBColorTable((HDC)hObj, iStart, cEntries, (RGBQUAD*)pEntries);
+ break;
}
- _SEH_END
+
+ if (pEntries)
+ {
+ if (!bInbound)
+ {
+ _SEH_TRY
+ {
+ ProbeForWrite(pUnsafeEntries, cEntries * sizeof(PALETTEENTRY), 1);
+ memcpy(pUnsafeEntries, pEntries, cEntries * sizeof(PALETTEENTRY));
+ }
+ _SEH_HANDLE
+ {
+ ret = 0;
+ }
+ _SEH_END
+ }
+ ExFreePool(pEntries);
+ }
return ret;
}