Author: tkreuzer
Date: Mon Apr 23 18:31:08 2007
New Revision: 26472
URL:
http://svn.reactos.org/svn/reactos?rev=26472&view=rev
Log:
GetObject rewrite part one (gdi32)
- use switch/case instead of if
- SetLastError() only in the correct cases
- add additional object types
- restructure the code
- change to @implemented
Before someone reverts everything: I have testcases. 129/132 tests pass now (this is
without EXTLOGPEN tests)
Modified:
trunk/reactos/dll/win32/gdi32/objects/dc.c
Modified: trunk/reactos/dll/win32/gdi32/objects/dc.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/dll/win32/gdi32/objects/dc…
==============================================================================
--- trunk/reactos/dll/win32/gdi32/objects/dc.c (original)
+++ trunk/reactos/dll/win32/gdi32/objects/dc.c Mon Apr 23 18:31:08 2007
@@ -395,125 +395,159 @@
int
-GetNonFontObject(HGDIOBJ Handle, int Size, LPVOID Buffer)
-{
- INT Type = GDI_HANDLE_GET_TYPE(Handle);
-
- if (Type == GDI_OBJECT_TYPE_REGION) // Not on the check list, so bye.
+GetNonFontObject(HGDIOBJ hGdiObj, int cbSize, LPVOID lpBuffer)
+{
+ INT dwType = GDI_HANDLE_GET_TYPE(hGdiObj);
+
+ switch(dwType)
{
- SetLastError(ERROR_INVALID_HANDLE);
- return 0;
+ case GDI_OBJECT_TYPE_DC:
+ case GDI_OBJECT_TYPE_REGION:
+ case GDI_OBJECT_TYPE_METAFILE:
+ case GDI_OBJECT_TYPE_ENHMETAFILE:
+ case GDI_OBJECT_TYPE_EMF:
+ SetLastError(ERROR_INVALID_HANDLE);
+ return 0;
+
+ case GDI_OBJECT_TYPE_COLORSPACE:
+ SetLastError(ERROR_NOT_SUPPORTED);
+ return 0;
+
+ case GDI_OBJECT_TYPE_PEN:
+ case GDI_OBJECT_TYPE_BRUSH:
+ case GDI_OBJECT_TYPE_BITMAP:
+ case GDI_OBJECT_TYPE_PALETTE:
+ case GDI_OBJECT_TYPE_METADC:
+ if (!lpBuffer)
+ {
+ switch(dwType)
+ {
+ case GDI_OBJECT_TYPE_PEN:
+ return sizeof(LOGPEN);
+ case GDI_OBJECT_TYPE_BRUSH:
+ return sizeof(LOGBRUSH);
+ case GDI_OBJECT_TYPE_BITMAP:
+ return sizeof(BITMAP);
+ case GDI_OBJECT_TYPE_PALETTE:
+ return sizeof(WORD);
+ case GDI_OBJECT_TYPE_METADC:
+ /* Windows does not SetLastError() in this case, more investigation needed
*/
+ return 0;
+ case GDI_OBJECT_TYPE_COLORSPACE: /* yes, windows acts like this */
+ SetLastError(ERROR_INSUFFICIENT_BUFFER);
+ return 60; // FIXME: what structure is this? */
+ case GDI_OBJECT_TYPE_EXTPEN: /* we don't know the size, ask win32k */
+ break;
+ default:
+ /* Other invalid handle type, windows does not SetLastError() */
+ return 0;
+ }
+ }
+ //Handle = GdiFixUpHandle(hGdiObj); new system is not ready
+ return NtGdiExtGetObjectW(hGdiObj, cbSize, lpBuffer);
}
-
- if (Buffer == NULL)
- {
- if (Type == GDI_OBJECT_TYPE_PEN) return sizeof(LOGPEN);
- else if (Type == GDI_OBJECT_TYPE_REGION) return sizeof(LOGBRUSH);
- }
-
- //Handle = GdiFixUpHandle(Handle); new system is not ready
-
- return NtGdiExtGetObjectW(Handle, Size, Buffer);
-}
-
-
-/*
- * @unimplemented
+ return 0;
+}
+
+
+/*
+ * @implemented
*/
int
STDCALL
-GetObjectA(HGDIOBJ Handle, int Size, LPVOID Buffer)
+GetObjectA(HGDIOBJ hGdiObj, int cbSize, LPVOID lpBuffer)
{
EXTLOGFONTW ExtLogFontW;
- DWORD Type;
+ LOGFONTA LogFontA;
+
+ DWORD dwType;
int Result = 0;
- Type = GDI_HANDLE_GET_TYPE(Handle);
-
- if((Type == GDI_OBJECT_TYPE_DC) ||
- (Type == GDI_OBJECT_TYPE_METAFILE) ||
- (Type == GDI_OBJECT_TYPE_ENHMETAFILE))
+ dwType = GDI_HANDLE_GET_TYPE(hGdiObj);;
+
+ if (dwType == GDI_OBJECT_TYPE_FONT)
{
- SetLastError(ERROR_INVALID_HANDLE);
- return 0;
- }
-
- if(Type == GDI_OBJECT_TYPE_COLORSPACE)
- {
- SetLastError(ERROR_NOT_SUPPORTED);
- return 0;
- }
-
- if (Type == GDI_OBJECT_TYPE_FONT)
- {
- if ( Buffer == NULL) return sizeof(LOGFONTA);
-
- if (Size < (int)sizeof(LOGFONTA))
- {
- SetLastError(ERROR_BUFFER_OVERFLOW);
- return 0;
- }
- Result = NtGdiExtGetObjectW(Handle, sizeof(EXTLOGFONTW), &ExtLogFontW);
- if (0 == Result)
- {
- return 0;
- }
+ if (!lpBuffer)
+ {
+ return sizeof(LOGFONTA);
+ }
+ if (cbSize == 0)
+ {
+ /* Windows does not SetLastError() */
+ return 0;
+ }
+ Result = NtGdiExtGetObjectW(hGdiObj, sizeof(EXTLOGFONTW), &ExtLogFontW);
+ if (0 == Result)
+ {
+ return 0;
+ }
+ LogFontW2A(&LogFontA, &ExtLogFontW.elfLogFont);
+
+ /* FIXME: windows writes up to 260 bytes */
+ /* What structure is that? */
+ if ((UINT)cbSize > 260)
+ {
+ cbSize = 260;
+ }
+ memcpy(lpBuffer, &LogFontA, cbSize);
/*
During testing of font objects, I passed ENUM/EXT/LOGFONT/EX/W to
NtGdiExtGetObjectW.
I think it likes EXTLOGFONTW. So,,, How do we handle the rest when a
caller wants to use E/E/L/E/A structures. Check for size? More research~
*/
- LogFontW2A((LPLOGFONTA) Buffer, &ExtLogFontW.elfLogFont);
- Result = sizeof(LOGFONTA);
- }
- else
- {
- Result = GetNonFontObject(Handle, Size, Buffer);
- }
-
- return Result;
-}
-
-
-/*
- * @unimplemented
+ return cbSize;
+ }
+
+ return GetNonFontObject(hGdiObj, cbSize, lpBuffer);
+}
+
+
+/*
+ * @implemented
*/
int
STDCALL
-GetObjectW(HGDIOBJ Handle, int Size, LPVOID Buffer)
-{
-
- INT Type = GDI_HANDLE_GET_TYPE(Handle);
+GetObjectW(HGDIOBJ hGdiObj, int cbSize, LPVOID lpBuffer)
+{
+ DWORD dwType = GDI_HANDLE_GET_TYPE(hGdiObj);
+ EXTLOGFONTW ExtLogFontW;
+ int Result = 0;
+
/*
Check List:
MSDN, "This can be a handle to one of the following: logical bitmap, a brush,
a font, a palette, a pen, or a device independent bitmap created by calling
the CreateDIBSection function."
*/
- if((Type == GDI_OBJECT_TYPE_DC) || // Yes, can not pass a normal DC!
- (Type == GDI_OBJECT_TYPE_METAFILE) ||
- (Type == GDI_OBJECT_TYPE_ENHMETAFILE))
+
+ if (dwType == GDI_OBJECT_TYPE_FONT)
{
- SetLastError(ERROR_INVALID_HANDLE);
- return 0;
+ if (!lpBuffer)
+ {
+ return sizeof(LOGFONTW);
+ }
+ if (cbSize == 0)
+ {
+ /* Windows does not SetLastError() */
+ return 0;
+ }
+ Result = NtGdiExtGetObjectW(hGdiObj, sizeof(EXTLOGFONTW), &ExtLogFontW);
+ if (0 == Result)
+ {
+ return 0;
+ }
+ /* FIXME: windows writes up to 356 bytes */
+ /* What structure is that? */
+ if ((UINT)cbSize > 356)
+ {
+ /* windows seems to delete the font in this case, more investigation needed */
+ cbSize = 356;
+ }
+ memcpy(lpBuffer, &ExtLogFontW.elfLogFont, cbSize);
+ return cbSize;
}
- if(Type == GDI_OBJECT_TYPE_COLORSPACE)
- {
- SetLastError(ERROR_NOT_SUPPORTED); // Not supported yet.
- return 0;
- }
-
- if(Type == GDI_OBJECT_TYPE_FONT)
- {
- if(Buffer == NULL) return sizeof(LOGFONTW);
-
- if(Size > sizeof(EXTLOGFONTW)) Size = sizeof(EXTLOGFONTW);
-
- return NtGdiExtGetObjectW(Handle, Size, Buffer);
- }
- else
- return GetNonFontObject(Handle, Size, Buffer);
+ return GetNonFontObject(hGdiObj, cbSize, lpBuffer);
}