Changed DC hook and abort proc handling to avoid having to allocate

thunks dynamically.
This commit is contained in:
Alexandre Julliard 2001-12-17 20:58:06 +00:00
parent f12e130fc2
commit 7d155d6706
9 changed files with 79 additions and 49 deletions

View File

@ -421,3 +421,4 @@ debug_channels (bitblt bitmap clipping dc ddraw driver enhmetafile font gdi
#
@ stdcall CreateMetaFile16(str) CreateMetaFile16
@ stdcall CloseMetaFile16(long) CloseMetaFile16
@ stdcall SetDCHook(long ptr long) SetDCHook

View File

@ -17,6 +17,7 @@
#include <unistd.h>
#include <fcntl.h>
#include "winbase.h"
#include "winuser.h"
#include "wine/winbase16.h"
#include "wine/wingdi16.h"
#include "winspool.h"
@ -24,7 +25,6 @@
#include "winreg.h"
#include "debugtools.h"
#include "gdi.h"
#include "callback.h"
#include "heap.h"
#include "file.h"
@ -250,14 +250,32 @@ extern WORD CALLBACK PRTDRV_CallTo16_word_ww(FARPROC16,WORD,WORD);
/* ### stop build ### */
/**********************************************************************
* SetAbortProc (GDI.381)
*
* call_abort_proc16
*/
INT16 WINAPI SetAbortProc16(HDC16 hdc, SEGPTR abrtprc)
static BOOL CALLBACK call_abort_proc16( HDC hdc, INT code )
{
ABORTPROC proc32 = (ABORTPROC)THUNK_Alloc((FARPROC16)abrtprc,
(RELAY)PRTDRV_CallTo16_word_ww);
return SetAbortProc(hdc, proc32);
ABORTPROC16 proc16;
DC *dc = DC_GetDCPtr( hdc );
if (!dc) return FALSE;
proc16 = dc->pAbortProc16;
GDI_ReleaseObj( hdc );
if (proc16) return PRTDRV_CallTo16_word_ww( (FARPROC16)proc16, hdc, code );
return TRUE;
}
/**********************************************************************
* SetAbortProc (GDI.381)
*/
INT16 WINAPI SetAbortProc16(HDC16 hdc, ABORTPROC16 abrtprc)
{
DC *dc = DC_GetDCPtr( hdc );
if (!dc) return FALSE;
dc->pAbortProc16 = abrtprc;
GDI_ReleaseObj( hdc );
return SetAbortProc( hdc, call_abort_proc16 );
}
/**********************************************************************
@ -268,7 +286,7 @@ INT WINAPI SetAbortProc(HDC hdc, ABORTPROC abrtprc)
{
DC *dc = DC_GetDCPtr( hdc );
if(dc->pAbortProc) THUNK_Free((FARPROC)dc->pAbortProc);
if (!dc) return FALSE;
dc->pAbortProc = abrtprc;
GDI_ReleaseObj( hdc );
return TRUE;

View File

@ -103,7 +103,7 @@ INT16 WINAPI Escape16( HDC16 hdc, INT16 escape, INT16 in_count,
/* Escape(hdc,SETABORTPROC,ABORTPROC,NULL); */
case SETABORTPROC:
return SetAbortProc16( hdc, in_data );
return SetAbortProc16( hdc, (ABORTPROC16)in_data );
/* Escape(hdc,STARTDOC,LPSTR,LPDOCINFO16);
* lpvOutData is actually a pointer to the DocInfo structure and used as

View File

@ -46,8 +46,6 @@ typedef struct tagGDIOBJHDR
} GDIOBJHDR;
typedef BOOL16 CALLBACK (*DCHOOKPROC)(HDC16,WORD,DWORD,LPARAM);
typedef struct tagGdiFont *GdiFont;
typedef struct tagDC
@ -109,6 +107,7 @@ typedef struct tagDC
INT DCOrgX; /* DC origin */
INT DCOrgY;
ABORTPROC pAbortProc; /* AbortProc for Printing */
ABORTPROC16 pAbortProc16;
INT CursPosX; /* Current position */
INT CursPosY;
INT ArcDirection;

View File

@ -216,11 +216,13 @@ typedef struct
FONTSIGNATURE ntmFontSig;
} NEWTEXTMETRICEX16,*LPNEWTEXTMETRICEX16;
typedef BOOL16 CALLBACK (*DCHOOKPROC)(HDC16,WORD,DWORD,LPARAM);
typedef INT16 CALLBACK (*FONTENUMPROC16)(SEGPTR,SEGPTR,UINT16,LPARAM);
typedef INT16 CALLBACK (*FONTENUMPROCEX16)(SEGPTR,SEGPTR,UINT16,LPARAM);
typedef VOID CALLBACK (*LINEDDAPROC16)(INT16,INT16,LPARAM);
typedef INT16 CALLBACK (*GOBJENUMPROC16)(SEGPTR,LPARAM);
typedef struct
{
UINT16 gmBlackBoxX;
@ -505,7 +507,7 @@ BOOL16 WINAPI SelectClipPath16(HDC16,INT16);
INT16 WINAPI SelectClipRgn16(HDC16,HRGN16);
HGDIOBJ16 WINAPI SelectObject16(HDC16,HGDIOBJ16);
INT16 WINAPI SelectVisRgn16(HDC16,HRGN16);
INT16 WINAPI SetAbortProc16(HDC16,SEGPTR);
INT16 WINAPI SetAbortProc16(HDC16,ABORTPROC16);
INT16 WINAPI SetArcDirection16(HDC16,INT16);
LONG WINAPI SetBitmapBits16(HBITMAP16,LONG,LPCVOID);
DWORD WINAPI SetBitmapDimension16(HBITMAP16,INT16,INT16);
@ -514,7 +516,8 @@ COLORREF WINAPI SetBkColor16(HDC16,COLORREF);
INT16 WINAPI SetBkMode16(HDC16,INT16);
UINT16 WINAPI SetBoundsRect16(HDC16,const RECT16*,UINT16);
DWORD WINAPI SetBrushOrg16(HDC16,INT16,INT16);
BOOL16 WINAPI SetDCHook(HDC16,FARPROC16,DWORD);
BOOL WINAPI SetDCHook(HDC,DCHOOKPROC,DWORD);
BOOL16 WINAPI SetDCHook16(HDC16,FARPROC16,DWORD);
DWORD WINAPI SetDCOrg16(HDC16,INT16,INT16);
VOID WINAPI SetDCState16(HDC16,HDC16);
UINT16 WINAPI SetDIBColorTable16(HDC16,UINT16,UINT16,RGBQUAD*);

View File

@ -1,2 +1,6 @@
Makefile
dc.glue.c
font.glue.c
gdiobj.glue.c
linedda.glue.c
metafile.glue.c

View File

@ -23,7 +23,12 @@ C_SRCS = \
region.c \
text.c
GLUE = dc.c
GLUE = \
dc.c \
font.c \
gdiobj.c \
linedda.c \
metafile.c
all: $(MODULE).o

View File

@ -13,7 +13,6 @@
#include "heap.h"
#include "debugtools.h"
#include "font.h"
#include "callback.h"
#include "winerror.h"
#include "windef.h"
#include "wingdi.h"
@ -21,6 +20,9 @@
DEFAULT_DEBUG_CHANNEL(dc);
/* ### start build ### */
extern WORD CALLBACK GDI_CallTo16_word_wwll(FARPROC16,WORD,WORD,LONG,LONG);
/* ### stop build ### */
/***********************************************************************
* DC_AllocDC
@ -773,8 +775,6 @@ BOOL WINAPI DeleteDC( HDC hdc )
if (dc->hClipRgn) DeleteObject( dc->hClipRgn );
if (dc->hVisRgn) DeleteObject( dc->hVisRgn );
if (dc->hGCClipRgn) DeleteObject( dc->hGCClipRgn );
if (dc->pAbortProc) THUNK_Free( (FARPROC)dc->pAbortProc );
if (dc->hookThunk) THUNK_Free( (FARPROC)dc->hookThunk );
if (dc->gdiFont) WineEngDecRefFont( dc->gdiFont );
PATH_DestroyGdiPath(&dc->path);
@ -1180,44 +1180,46 @@ BOOL WINAPI CombineTransform( LPXFORM xformResult, const XFORM *xform1,
}
/***********************************************************************
* SetDCHook (GDI32.@)
*
* Note: this doesn't exist in Win32, we add it here because user32 needs it.
*/
BOOL WINAPI SetDCHook( HDC hdc, DCHOOKPROC hookProc, DWORD dwHookData )
{
DC *dc = DC_GetDCPtr( hdc );
if (!dc) return FALSE;
dc->dwHookData = dwHookData;
dc->hookThunk = hookProc;
GDI_ReleaseObj( hdc );
return TRUE;
}
/* relay function to call the 16-bit DC hook proc */
static BOOL16 WINAPI call_dc_hook16( HDC16 hdc, WORD code, DWORD data, LPARAM lParam )
{
FARPROC16 proc = NULL;
DC *dc = DC_GetDCPtr( hdc );
if (!dc) return FALSE;
proc = dc->hookProc;
GDI_ReleaseObj( hdc );
if (!proc) return FALSE;
return GDI_CallTo16_word_wwll( proc, hdc, code, data, lParam );
}
/***********************************************************************
* SetDCHook (GDI.190)
*/
/* ### start build ### */
extern WORD CALLBACK GDI_CallTo16_word_wwll(FARPROC16,WORD,WORD,LONG,LONG);
/* ### stop build ### */
/**********************************************************************/
BOOL16 WINAPI SetDCHook( HDC16 hdc, FARPROC16 hookProc, DWORD dwHookData )
BOOL16 WINAPI SetDCHook16( HDC16 hdc, FARPROC16 hookProc, DWORD dwHookData )
{
DC *dc = DC_GetDCPtr( hdc );
if (!dc) return FALSE;
/*
* Note: We store the original SEGPTR 'hookProc' as we need to be
* able to return it verbatim in GetDCHook,
*
* On the other hand, we still call THUNK_Alloc and store the
* 32-bit thunk into another DC member, because THUNK_Alloc
* recognizes the (typical) case that the 'hookProc' is indeed
* the 16-bit API entry point of a built-in routine (e.g. DCHook16)
*
* We could perform that test every time the hook is about to
* be called (or else we could live with the 32->16->32 detour),
* but this way is the most efficient ...
*/
dc->hookProc = hookProc;
dc->dwHookData = dwHookData;
THUNK_Free( (FARPROC)dc->hookThunk );
dc->hookThunk = (DCHOOKPROC)
THUNK_Alloc( hookProc, (RELAY)GDI_CallTo16_word_wwll );
GDI_ReleaseObj( hdc );
return TRUE;
return SetDCHook( hdc, call_dc_hook16, dwHookData );
}

View File

@ -68,7 +68,6 @@ static void DCE_DumpCache(void)
*/
DCE *DCE_AllocDCE( HWND hWnd, DCE_TYPE type )
{
FARPROC16 hookProc;
DCE * dce;
if (!(dce = HeapAlloc( GetProcessHeap(), 0, sizeof(DCE) ))) return NULL;
@ -81,8 +80,7 @@ DCE *DCE_AllocDCE( HWND hWnd, DCE_TYPE type )
/* store DCE handle in DC hook data field */
hookProc = GetProcAddress16( GetModuleHandle16("USER"), (LPCSTR)362 );
SetDCHook( dce->hDC, hookProc, (DWORD)dce );
SetDCHook( dce->hDC, DCHook16, (DWORD)dce );
dce->hwndCurrent = WIN_GetFullHandle( hWnd );
dce->hClipRgn = 0;