Turn a GDI object into a system object via an explicit Wine extension
rather then through magical pokes in memory.
This commit is contained in:
parent
70bc9f39f1
commit
2a109307c3
|
@ -431,6 +431,15 @@
|
||||||
@ stdcall SetHookFlags16(long long)
|
@ stdcall SetHookFlags16(long long)
|
||||||
@ stdcall WriteSpool16(long ptr long)
|
@ stdcall WriteSpool16(long ptr long)
|
||||||
|
|
||||||
|
################################################################
|
||||||
|
# Wine internal extensions
|
||||||
|
#
|
||||||
|
# All functions must be prefixed with '__wine_' (for internal functions)
|
||||||
|
# or 'wine_' (for user-visible functions) to avoid namespace conflicts.
|
||||||
|
|
||||||
|
# GDI objects
|
||||||
|
@ cdecl __wine_make_gdi_object_system(long long)
|
||||||
|
|
||||||
################################################################
|
################################################################
|
||||||
# Wine dll separation hacks, these will go away, don't use them
|
# Wine dll separation hacks, these will go away, don't use them
|
||||||
#
|
#
|
||||||
|
|
|
@ -445,6 +445,26 @@ static const struct DefaultFontInfo default_fonts[] =
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*************************************************************************
|
||||||
|
* __wine_make_gdi_object_system (GDI32.@)
|
||||||
|
*
|
||||||
|
* USER has to tell GDI that its system brushes and pens are non-deletable.
|
||||||
|
* For a description of the GDI object magics and their flags,
|
||||||
|
* see "Undocumented Windows" (wrong about the OBJECT_NOSYSTEM flag, though).
|
||||||
|
*/
|
||||||
|
void __wine_make_gdi_object_system( HGDIOBJ handle, BOOL set)
|
||||||
|
{
|
||||||
|
GDIOBJHDR *ptr = GDI_GetObjPtr( handle, MAGIC_DONTCARE );
|
||||||
|
|
||||||
|
/* touch the "system" bit of the wMagic field of a GDIOBJHDR */
|
||||||
|
if (set)
|
||||||
|
ptr->wMagic &= ~OBJECT_NOSYSTEM;
|
||||||
|
else
|
||||||
|
ptr->wMagic |= OBJECT_NOSYSTEM;
|
||||||
|
|
||||||
|
GDI_ReleaseObj( handle );
|
||||||
|
}
|
||||||
|
|
||||||
/******************************************************************************
|
/******************************************************************************
|
||||||
* get_default_fonts
|
* get_default_fonts
|
||||||
*/
|
*/
|
||||||
|
@ -604,7 +624,6 @@ BOOL GDI_Init(void)
|
||||||
{
|
{
|
||||||
HINSTANCE16 instance;
|
HINSTANCE16 instance;
|
||||||
HKEY hkey;
|
HKEY hkey;
|
||||||
GDIOBJHDR *ptr;
|
|
||||||
LOGFONTW default_gui_font;
|
LOGFONTW default_gui_font;
|
||||||
const struct DefaultFontInfo* deffonts;
|
const struct DefaultFontInfo* deffonts;
|
||||||
int i;
|
int i;
|
||||||
|
@ -659,9 +678,7 @@ BOOL GDI_Init(void)
|
||||||
ERR( "could not create stock object %d\n", i );
|
ERR( "could not create stock object %d\n", i );
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
ptr = GDI_GetObjPtr( stock_objects[i], MAGIC_DONTCARE );
|
__wine_make_gdi_object_system( stock_objects[i], TRUE );
|
||||||
ptr->wMagic &= ~OBJECT_NOSYSTEM;
|
|
||||||
GDI_ReleaseObj( stock_objects[i] );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (hkey) RegCloseKey( hkey );
|
if (hkey) RegCloseKey( hkey );
|
||||||
|
|
|
@ -27,13 +27,9 @@
|
||||||
#include "windef.h"
|
#include "windef.h"
|
||||||
#include "winbase.h"
|
#include "winbase.h"
|
||||||
#include "wingdi.h"
|
#include "wingdi.h"
|
||||||
#include "wine/winbase16.h"
|
|
||||||
#include "wine/winuser16.h"
|
|
||||||
#include "winuser.h"
|
#include "winuser.h"
|
||||||
#include "wownt32.h"
|
|
||||||
#include "winreg.h"
|
#include "winreg.h"
|
||||||
#include "winternl.h"
|
#include "winternl.h"
|
||||||
#include "gdi.h" /* sic */
|
|
||||||
#include "wine/debug.h"
|
#include "wine/debug.h"
|
||||||
|
|
||||||
WINE_DEFAULT_DEBUG_CHANNEL(syscolor);
|
WINE_DEFAULT_DEBUG_CHANNEL(syscolor);
|
||||||
|
@ -85,41 +81,7 @@ static const WORD wPattern55AA[] =
|
||||||
|
|
||||||
HBRUSH SYSCOLOR_55AABrush = 0;
|
HBRUSH SYSCOLOR_55AABrush = 0;
|
||||||
|
|
||||||
|
extern void __wine_make_gdi_object_system( HGDIOBJ handle, BOOL set );
|
||||||
/*************************************************************************
|
|
||||||
* SYSCOLOR_MakeObjectSystem
|
|
||||||
*
|
|
||||||
* OK, now for a very ugly hack.
|
|
||||||
* USER somehow has to tell GDI that its system brushes and pens are
|
|
||||||
* non-deletable.
|
|
||||||
* We don't want to export a function from GDI doing this for us,
|
|
||||||
* so we just do that ourselves by "wildly flipping some bits in memory".
|
|
||||||
* For a description of the GDI object magics and their flags,
|
|
||||||
* see "Undocumented Windows" (wrong about the OBJECT_NOSYSTEM flag, though).
|
|
||||||
*/
|
|
||||||
static void SYSCOLOR_MakeObjectSystem( HGDIOBJ16 handle, BOOL set)
|
|
||||||
{
|
|
||||||
static WORD heap_sel = 0;
|
|
||||||
LPWORD ptr;
|
|
||||||
|
|
||||||
if (!heap_sel) heap_sel = LoadLibrary16( "gdi" );
|
|
||||||
if (heap_sel >= 32)
|
|
||||||
{
|
|
||||||
STACK16FRAME* stack16 = MapSL((SEGPTR)NtCurrentTeb()->WOW32Reserved);
|
|
||||||
HANDLE16 oldDS = stack16->ds;
|
|
||||||
|
|
||||||
stack16->ds = heap_sel;
|
|
||||||
ptr = MapSL(LocalLock16(handle));
|
|
||||||
|
|
||||||
/* touch the "system" bit of the wMagic field of a GDIOBJHDR */
|
|
||||||
if (set)
|
|
||||||
*ptr &= ~OBJECT_NOSYSTEM;
|
|
||||||
else
|
|
||||||
*ptr |= OBJECT_NOSYSTEM;
|
|
||||||
LocalUnlock16( handle );
|
|
||||||
stack16->ds = oldDS;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/*************************************************************************
|
/*************************************************************************
|
||||||
* SYSCOLOR_SetColor
|
* SYSCOLOR_SetColor
|
||||||
|
@ -130,19 +92,19 @@ static void SYSCOLOR_SetColor( int index, COLORREF color )
|
||||||
SysColors[index] = color;
|
SysColors[index] = color;
|
||||||
if (SysColorBrushes[index])
|
if (SysColorBrushes[index])
|
||||||
{
|
{
|
||||||
SYSCOLOR_MakeObjectSystem( HBRUSH_16(SysColorBrushes[index]), FALSE);
|
__wine_make_gdi_object_system( SysColorBrushes[index], FALSE);
|
||||||
DeleteObject( SysColorBrushes[index] );
|
DeleteObject( SysColorBrushes[index] );
|
||||||
}
|
}
|
||||||
SysColorBrushes[index] = CreateSolidBrush( color );
|
SysColorBrushes[index] = CreateSolidBrush( color );
|
||||||
SYSCOLOR_MakeObjectSystem( HBRUSH_16(SysColorBrushes[index]), TRUE);
|
__wine_make_gdi_object_system( SysColorBrushes[index], TRUE);
|
||||||
|
|
||||||
if (SysColorPens[index])
|
if (SysColorPens[index])
|
||||||
{
|
{
|
||||||
SYSCOLOR_MakeObjectSystem( HPEN_16(SysColorPens[index]), FALSE);
|
__wine_make_gdi_object_system( SysColorPens[index], FALSE);
|
||||||
DeleteObject( SysColorPens[index] );
|
DeleteObject( SysColorPens[index] );
|
||||||
}
|
}
|
||||||
SysColorPens[index] = CreatePen( PS_SOLID, 1, color );
|
SysColorPens[index] = CreatePen( PS_SOLID, 1, color );
|
||||||
SYSCOLOR_MakeObjectSystem( HPEN_16(SysColorPens[index]), TRUE);
|
__wine_make_gdi_object_system( SysColorPens[index], TRUE);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -192,7 +154,7 @@ void SYSCOLOR_Init(void)
|
||||||
|
|
||||||
h55AABitmap = CreateBitmap( 8, 8, 1, 1, wPattern55AA );
|
h55AABitmap = CreateBitmap( 8, 8, 1, 1, wPattern55AA );
|
||||||
SYSCOLOR_55AABrush = CreatePatternBrush( h55AABitmap );
|
SYSCOLOR_55AABrush = CreatePatternBrush( h55AABitmap );
|
||||||
SYSCOLOR_MakeObjectSystem( HBRUSH_16(SYSCOLOR_55AABrush), TRUE );
|
__wine_make_gdi_object_system( SYSCOLOR_55AABrush, TRUE );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue