ReactOS 0.4.15-dev-7953-g1f49173
icm.c
Go to the documentation of this file.
1/*
2 * PROJECT: ReactOS Win32k Subsystem
3 * LICENSE: GPL - See COPYING in the top level directory
4 * FILE: win32ss/gdi/ntgdi/icm.c
5 * PURPOSE: Icm functions
6 * PROGRAMMERS: ...
7 */
8
9#include <win32k.h>
10
11#define NDEBUG
12#include <debug.h>
13
14HCOLORSPACE hStockColorSpace = NULL;
15
16
17HCOLORSPACE
21{
22 PCOLORSPACE pCS;
23 HCOLORSPACE hCS;
24
26 if (pCS == NULL) return NULL;
27
28 hCS = pCS->BaseObject.hHmgr;
29
30 pCS->lcsColorSpace = pLogColorSpace->lcsColorSpace;
31 pCS->dwFlags = pLogColorSpace->dwFlags;
32
34 return hCS;
35}
36
37BOOL
40 HCOLORSPACE hColorSpace)
41{
42 BOOL Ret = FALSE;
43
44 if ((hColorSpace != hStockColorSpace) &&
46 {
47 Ret = GreDeleteObject(hColorSpace);
49 }
50
51 return Ret;
52}
53
58{
59 LOGCOLORSPACEEXW Safelcs;
61
63 {
66 }
68 {
70 }
72
73 if (!NT_SUCCESS(Status))
74 {
76 return NULL;
77 }
78
79 return IntGdiCreateColorSpace(&Safelcs);
80}
81
82BOOL
85 IN HANDLE hColorSpace)
86{
87 return IntGdiDeleteColorSpace(hColorSpace);
88}
89
90BOOL
93{
94 PPDEVOBJ pGDev = (PPDEVOBJ) hPDev;
95 int i;
96
97 if (!(pGDev->flFlags & PDEV_DISPLAY)) return FALSE;
98
99 if ((pGDev->devinfo.iDitherFormat == BMF_8BPP) ||
100 (pGDev->devinfo.iDitherFormat == BMF_16BPP) ||
101 (pGDev->devinfo.iDitherFormat == BMF_24BPP) ||
102 (pGDev->devinfo.iDitherFormat == BMF_32BPP))
103 {
104 if (pGDev->flFlags & PDEV_GAMMARAMP_TABLE)
105 {
106 RtlCopyMemory(Ramp, pGDev->pvGammaRamp, sizeof(GAMMARAMP));
107 }
108 else
109 {
110 // Generate the 256-colors array
111 for (i = 0; i < 256; i++ )
112 {
113 int NewValue = i * 256;
114
115 Ramp->Red[i] = Ramp->Green[i] = Ramp->Blue[i] = ((WORD)NewValue);
116 }
117 }
118 return TRUE;
119 }
120
121 return FALSE;
122}
123
124BOOL
127 HDC hDC,
128 LPVOID Ramp)
129{
130 BOOL Ret;
131 PDC dc;
133 PGAMMARAMP SafeRamp;
134
135 if (!Ramp) return FALSE;
136
137 dc = DC_LockDc(hDC);
138 if (!dc)
139 {
141 return FALSE;
142 }
143
145 if (!SafeRamp)
146 {
149 return FALSE;
150 }
151
152 Ret = IntGetDeviceGammaRamp((HDEV)dc->ppdev, SafeRamp);
153 if (!Ret)
154 {
156 ExFreePoolWithTag(SafeRamp, GDITAG_ICM);
157 return Ret;
158 }
159
161 {
162 ProbeForWrite(Ramp, sizeof(GAMMARAMP), 1);
163 RtlCopyMemory(Ramp, SafeRamp, sizeof(GAMMARAMP));
164 }
166 {
168 }
169 _SEH2_END;
170
172 ExFreePoolWithTag(SafeRamp, GDITAG_ICM);
173
174 if (!NT_SUCCESS(Status))
175 {
177 return FALSE;
178 }
179 return Ret;
180}
181
182BOOL
185 IN HCOLORSPACE hColorSpace)
186{
187 PDC pDC;
188 PDC_ATTR pdcattr;
189 PCOLORSPACE pCS;
190
191 pDC = DC_LockDc(hdc);
192 if (!pDC)
193 {
195 return FALSE;
196 }
197 pdcattr = pDC->pdcattr;
198
199 if (pdcattr->hColorSpace == hColorSpace)
200 {
201 DC_UnlockDc(pDC);
202 return TRUE;
203 }
204
205 pCS = COLORSPACEOBJ_LockCS(hColorSpace);
206 if (!pCS)
207 {
209 return FALSE;
210 }
211
212 if (pDC->dclevel.pColorSpace)
213 {
214 GDIOBJ_vDereferenceObject((POBJ) pDC->dclevel.pColorSpace);
215 }
216
217 pDC->dclevel.pColorSpace = pCS;
218 pdcattr->hColorSpace = hColorSpace;
219
221 DC_UnlockDc(pDC);
222 return TRUE;
223}
224
225BOOL
228{
229 BOOL Ret = FALSE;
230 PPALETTE palGDI;
231 PALOBJ *palPtr;
232 PPDEVOBJ pGDev = (PPDEVOBJ)hPDev;
233
234 if ((pGDev->devinfo.iDitherFormat == BMF_8BPP) ||
235 (pGDev->devinfo.iDitherFormat == BMF_16BPP) ||
236 (pGDev->devinfo.iDitherFormat == BMF_24BPP) ||
237 (pGDev->devinfo.iDitherFormat == BMF_32BPP))
238 {
240 return pGDev->DriverFunctions.IcmSetDeviceGammaRamp( pGDev->dhpdev,
242 pGDev->pvGammaRamp);
243
244 if ((pGDev->devinfo.iDitherFormat != BMF_8BPP) ||
245 !(pGDev->gdiinfo.flRaster & RC_PALETTE)) return FALSE;
246
247 if (!(pGDev->flFlags & PDEV_GAMMARAMP_TABLE)) return FALSE;
248
250 if(!palGDI) return FALSE;
251 palPtr = (PALOBJ*) palGDI;
252
253 if (pGDev->flFlags & PDEV_GAMMARAMP_TABLE)
254 palGDI->flFlags |= PAL_GAMMACORRECTION;
255 else
256 palGDI->flFlags &= ~PAL_GAMMACORRECTION;
257
258 if (!(pGDev->flFlags & PDEV_DRIVER_PUNTED_CALL)) // No punting, we hook
259 {
260 // BMF_8BPP only!
261 // PALOBJ_cGetColors check mode flags and update Gamma Correction.
262 // Set the HDEV to pal and go.
263 palGDI->hPDev = hPDev;
264 Ret = pGDev->DriverFunctions.SetPalette(pGDev->dhpdev,
265 palPtr,
266 0,
267 0,
268 palGDI->NumColors);
269 }
271 return Ret;
272 }
273 else
274 return FALSE;
275}
276
277//
278// ICM registry subkey sets internal brightness range, gamma range is 128 or
279// 256 when icm is init.
280INT IcmGammaRangeSet = 128; // <- Make it global
281
282BOOL
285{
286 WORD IcmGR, i, R, G, B;
287 BOOL Ret = FALSE, TstPeak;
288 PPDEVOBJ pGDev = (PPDEVOBJ) hPDev;
289
290 if (!hPDev) return FALSE;
291
292 if (!(pGDev->flFlags & PDEV_DISPLAY )) return FALSE;
293
294 if ((pGDev->devinfo.iDitherFormat == BMF_8BPP) ||
295 (pGDev->devinfo.iDitherFormat == BMF_16BPP) ||
296 (pGDev->devinfo.iDitherFormat == BMF_24BPP) ||
297 (pGDev->devinfo.iDitherFormat == BMF_32BPP))
298 {
300 {
301 // No driver support
303 {
304 // Driver does not support Gamma Ramp, so test to see we
305 // have BMF_8BPP only and palette operation support.
306 if ((pGDev->devinfo.iDitherFormat != BMF_8BPP) ||
307 !(pGDev->gdiinfo.flRaster & RC_PALETTE)) return FALSE;
308 }
309 }
310
311 if (pGDev->flFlags & PDEV_GAMMARAMP_TABLE)
312 {
313 if (RtlCompareMemory(pGDev->pvGammaRamp, Ramp, sizeof(GAMMARAMP)) ==
314 sizeof(GAMMARAMP)) return TRUE;
315 }
316
317 // Verify Ramp is inside range.
318 IcmGR = -IcmGammaRangeSet;
319 TstPeak = (Test == FALSE);
320 for (i = 0; i < 256; i++)
321 {
322 R = Ramp->Red[i] / 256;
323 G = Ramp->Green[i] / 256;
324 B = Ramp->Blue[i] / 256;
325
326 if (R >= IcmGR)
327 {
328 if (R <= IcmGammaRangeSet + i)
329 {
330 if ((G >= IcmGR) &&
331 (G <= IcmGammaRangeSet + i) &&
332 (B >= IcmGR) &&
333 (B <= IcmGammaRangeSet + i) ) continue;
334 }
335 }
336
337 if (Test) return Ret; // Don't set and return.
338
339 // No test override, check max range
340 if (TstPeak)
341 {
342 if ((R != (IcmGR * 256)) ||
343 (G != (IcmGR * 256)) ||
344 (B != (IcmGR * 256)) ) TstPeak = FALSE; // W/i range.
345 }
346 }
347 // ReactOS allocates a ramp even if it is 8BPP and Palette only.
348 // This way we have a record of the change in memory.
349 if (!pGDev->pvGammaRamp && !(pGDev->flFlags & PDEV_GAMMARAMP_TABLE))
350 {
351 // If the above is true and we have nothing allocated, create it.
354 }
355
356 if (pGDev->pvGammaRamp)
357 RtlCopyMemory(pGDev->pvGammaRamp, Ramp, sizeof(GAMMARAMP));
358
359 Ret = UpdateDeviceGammaRamp(hPDev);
360 }
361
362 return Ret;
363}
364
365BOOL
368 HDC hDC,
369 LPVOID Ramp)
370{
371 BOOL Ret;
372 PDC dc;
374 PGAMMARAMP SafeRamp;
375 if (!Ramp) return FALSE;
376
377 dc = DC_LockDc(hDC);
378 if (!dc)
379 {
381 return FALSE;
382 }
383
385 if (!SafeRamp)
386 {
389 return FALSE;
390 }
392 {
393 ProbeForRead(Ramp, sizeof(GAMMARAMP), 1);
394 RtlCopyMemory(SafeRamp, Ramp, sizeof(GAMMARAMP));
395 }
397 {
399 }
400 _SEH2_END;
401
402 if (!NT_SUCCESS(Status))
403 {
405 ExFreePoolWithTag(SafeRamp, GDITAG_ICM);
407 return FALSE;
408 }
409
410 Ret = IntSetDeviceGammaRamp((HDEV)dc->ppdev, SafeRamp, TRUE);
412 ExFreePoolWithTag(SafeRamp, GDITAG_ICM);
413 return Ret;
414}
415
416INT
419 ULONG nCommand,
420 ULONG EnableICM) // ulMode
421{
422 /* FIXME: This should be coded someday */
423 if (EnableICM == ICM_OFF)
424 {
425 return ICM_OFF;
426 }
427 if (EnableICM == ICM_ON)
428 {
429 return 0;
430 }
431 if (EnableICM == ICM_QUERY)
432 {
433 return ICM_OFF;
434 }
435
436 return 0;
437}
438
439/* EOF */
static HDC hDC
Definition: 3dtext.c:33
LONG NTSTATUS
Definition: precomp.h:26
#define G(r, i, a, b, c, d)
Definition: blake2b-ref.c:117
HGDIOBJ hHmgr(VOID)
Definition: baseobj.hpp:95
Definition: ehthrow.cxx:54
#define COLORSPACEOBJ_AllocCSWithHandle()
Definition: color.h:18
#define COLORSPACEOBJ_UnlockCS(pCS)
Definition: color.h:20
#define COLORSPACEOBJ_LockCS(hCS)
Definition: color.h:19
FORCEINLINE VOID DC_UnlockDc(PDC pdc)
Definition: dc.h:238
FORCEINLINE PDC DC_LockDc(HDC hdc)
Definition: dc.h:220
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
#define APIENTRY
Definition: api.h:79
#define B(row, col)
#define ERROR_INVALID_PARAMETER
Definition: compat.h:101
#define ERROR_INVALID_HANDLE
Definition: compat.h:98
#define ExAllocatePoolWithTag(hernya, size, tag)
Definition: env_spec_w32.h:350
#define RtlCompareMemory(s1, s2, l)
Definition: env_spec_w32.h:465
#define PagedPool
Definition: env_spec_w32.h:308
VOID NTAPI ProbeForRead(IN CONST VOID *Address, IN SIZE_T Length, IN ULONG Alignment)
Definition: exintrin.c:102
VOID NTAPI ProbeForWrite(IN PVOID Address, IN SIZE_T Length, IN ULONG Alignment)
Definition: exintrin.c:143
#define _SEH2_END
Definition: filesup.c:22
#define _SEH2_TRY
Definition: filesup.c:19
unsigned int BOOL
Definition: ntddk_ex.h:94
unsigned short WORD
Definition: ntddk_ex.h:93
#define GDI_HANDLE_GET_TYPE(h)
Definition: gdi.h:31
@ GDILoObjType_LO_ICMLCS_TYPE
Definition: gdi_private.h:39
Status
Definition: gdiplustypes.h:25
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
#define EXCEPTION_EXECUTE_HANDLER
Definition: excpt.h:85
struct _PDEVOBJ * PPDEVOBJ
Definition: mdevobj.h:6
static const WCHAR dc[]
#define ExFreePoolWithTag(_P, _T)
Definition: module.h:1109
HDC hdc
Definition: main.c:9
static HDC
Definition: imagelist.c:92
#define FASTCALL
Definition: nt_native.h:50
__kernel_entry W32KAPI BOOL APIENTRY NtGdiSetColorSpace(_In_ HDC hdc, _In_ HCOLORSPACE hColorSpace)
__kernel_entry W32KAPI HANDLE APIENTRY NtGdiCreateColorSpace(_In_ PLOGCOLORSPACEEXW pLogColorSpace)
#define STATUS_NO_MEMORY
Definition: ntstatus.h:260
@ PDEV_DISPLAY
Definition: pdevobj.h:7
@ PDEV_GAMMARAMP_TABLE
Definition: pdevobj.h:17
@ PDEV_DRIVER_PUNTED_CALL
Definition: pdevobj.h:21
#define _SEH2_GetExceptionCode()
Definition: pseh2_64.h:159
#define _SEH2_EXCEPT(...)
Definition: pseh2_64.h:34
#define R(b, x)
Definition: sha2.c:134
#define STATUS_SUCCESS
Definition: shellext.h:65
Definition: polytest.cpp:41
DWORD dwFlags
Definition: color.h:13
LOGCOLORSPACEW lcsColorSpace
Definition: color.h:12
BASEOBJECT BaseObject
Definition: color.h:11
HCOLORSPACE hColorSpace
Definition: ntgdihdl.h:319
ULONG iDitherFormat
Definition: winddi.h:395
HPALETTE hpalDefault
Definition: winddi.h:398
FLONG flGraphicsCaps2
Definition: winddi.h:399
PFN_DrvSetPalette SetPalette
Definition: ntgdityp.h:591
PFN_DrvIcmSetDeviceGammaRamp IcmSetDeviceGammaRamp
Definition: ntgdityp.h:636
WORD Red[256]
Definition: winddi.h:775
WORD Blue[256]
Definition: winddi.h:777
WORD Green[256]
Definition: winddi.h:776
ULONG flRaster
Definition: winddi.h:887
HDEV hPDev
Definition: palette.h:49
ULONG NumColors
Definition: palette.h:41
FLONG flFlags
Definition: palette.h:40
FLONG flFlags
Definition: pdevobj.h:87
GDIINFO gdiinfo
Definition: pdevobj.h:123
DHPDEV dhpdev
Definition: pdevobj.h:120
PVOID pvGammaRamp
Definition: pdevobj.h:106
DRIVER_FUNCTIONS DriverFunctions
Definition: pdevobj.h:137
DEVINFO devinfo
Definition: pdevobj.h:122
int32_t INT
Definition: typedefs.h:58
#define RtlCopyMemory(Destination, Source, Length)
Definition: typedefs.h:263
#define IN
Definition: typedefs.h:39
uint32_t ULONG
Definition: typedefs.h:59
VOID FASTCALL SetLastNtError(_In_ NTSTATUS Status)
Definition: error.c:31
VOID NTAPI GDIOBJ_vDereferenceObject(POBJ pobj)
Definition: gdiobj.c:631
BOOL NTAPI GreDeleteObject(HGDIOBJ hobj)
Definition: gdiobj.c:1158
HCOLORSPACE FASTCALL IntGdiCreateColorSpace(PLOGCOLORSPACEEXW pLogColorSpace)
Definition: icm.c:19
HCOLORSPACE hStockColorSpace
Definition: icm.c:14
INT APIENTRY NtGdiSetIcmMode(HDC hDC, ULONG nCommand, ULONG EnableICM)
Definition: icm.c:418
BOOL APIENTRY NtGdiSetDeviceGammaRamp(HDC hDC, LPVOID Ramp)
Definition: icm.c:367
BOOL FASTCALL IntGetDeviceGammaRamp(HDEV hPDev, PGAMMARAMP Ramp)
Definition: icm.c:92
BOOL FASTCALL UpdateDeviceGammaRamp(HDEV hPDev)
Definition: icm.c:227
BOOL APIENTRY NtGdiGetDeviceGammaRamp(HDC hDC, LPVOID Ramp)
Definition: icm.c:126
BOOL APIENTRY NtGdiDeleteColorSpace(IN HANDLE hColorSpace)
Definition: icm.c:84
INT IcmGammaRangeSet
Definition: icm.c:280
BOOL FASTCALL IntGdiDeleteColorSpace(HCOLORSPACE hColorSpace)
Definition: icm.c:39
BOOL FASTCALL IntSetDeviceGammaRamp(HDEV hPDev, PGAMMARAMP Ramp, BOOL Test)
Definition: icm.c:284
@ PAL_GAMMACORRECTION
Definition: palette.h:29
#define PALETTE_ShareLockPalette(hpal)
Definition: palette.h:57
#define PALETTE_ShareUnlockPalette(ppal)
Definition: palette.h:59
#define GDITAG_ICM
Definition: tags.h:126
#define GCAPS2_CHANGEGAMMARAMP
Definition: winddi.h:370
#define BMF_16BPP
Definition: winddi.h:358
#define IGRF_RGB_256WORDS
Definition: winddi.h:3693
#define BMF_8BPP
Definition: winddi.h:357
_In_ LPLOGCOLORSPACEW pLogColorSpace
Definition: winddi.h:3673
#define BMF_24BPP
Definition: winddi.h:359
#define BMF_32BPP
Definition: winddi.h:360
ENGAPI VOID APIENTRY EngSetLastError(_In_ ULONG iError)
Definition: error.c:22
#define ICM_QUERY
Definition: wingdi.h:983
#define ICM_OFF
Definition: wingdi.h:982
#define ICM_ON
Definition: wingdi.h:981
#define RC_PALETTE
Definition: wingdi.h:790