Release 970509
[wine/multimedia.git] / if1632 / thunk.c
blob20f05cd894179ddb038b81f13286c3d2df3e9332
1 /*
2 * Emulator thunks
4 * Copyright 1996 Alexandre Julliard
5 */
7 #include "windows.h"
8 #include "callback.h"
9 #include "heap.h"
10 #include "hook.h"
11 #include "module.h"
12 #include "winproc.h"
13 #include "stackframe.h"
14 #include "except.h"
15 #include "stddebug.h"
16 #include "debug.h"
18 typedef void (*RELAY)();
20 #pragma pack(1)
22 typedef struct tagTHUNK
24 BYTE popl_eax; /* 0x58 popl %eax (return address)*/
25 BYTE pushl_func; /* 0x68 pushl $proc */
26 FARPROC32 proc WINE_PACKED;
27 BYTE pushl_eax; /* 0x50 pushl %eax */
28 BYTE jmp; /* 0xe9 jmp relay (relative jump)*/
29 RELAY relay WINE_PACKED;
30 struct tagTHUNK *next WINE_PACKED;
31 } THUNK;
33 #pragma pack(4)
35 #define DECL_THUNK(name,proc,relay) \
36 THUNK name = { 0x58, 0x68, (FARPROC32)(proc), 0x50, 0xe9, \
37 (RELAY)((char *)(relay) - (char *)(&(name).next)), NULL }
40 static THUNK *firstThunk = NULL;
42 static LRESULT THUNK_CallWndProc16( WNDPROC16 proc, HWND16 hwnd, UINT16 msg,
43 WPARAM16 wParam, LPARAM lParam );
45 /***********************************************************************
46 * THUNK_Init
48 BOOL32 THUNK_Init(void)
50 /* Set the window proc calling functions */
51 WINPROC_SetCallWndProc16( THUNK_CallWndProc16 );
52 WINPROC_SetCallWndProc32( (WINPROC_CALLWNDPROC32)CallTo32_4 );
53 return TRUE;
57 /***********************************************************************
58 * THUNK_Alloc
60 static THUNK *THUNK_Alloc( FARPROC32 func, RELAY relay )
62 THUNK *thunk = HeapAlloc( GetProcessHeap(), 0, sizeof(*thunk) );
63 if (thunk)
65 thunk->popl_eax = 0x58;
66 thunk->pushl_func = 0x68;
67 thunk->proc = func;
68 thunk->pushl_eax = 0x50;
69 thunk->jmp = 0xe9;
70 thunk->relay = (RELAY)((char *)relay - (char *)(&thunk->next));
71 thunk->next = firstThunk;
72 firstThunk = thunk;
74 return thunk;
78 /***********************************************************************
79 * THUNK_Find
81 static THUNK *THUNK_Find( FARPROC32 func )
83 THUNK *thunk = firstThunk;
84 while (thunk && (thunk->proc != func)) thunk = thunk->next;
85 return thunk;
89 /***********************************************************************
90 * THUNK_Free
92 static void THUNK_Free( THUNK *thunk )
94 if (HEAP_IsInsideHeap( GetProcessHeap(), 0, thunk ))
96 THUNK **prev = &firstThunk;
97 while (*prev && (*prev != thunk)) prev = &(*prev)->next;
98 if (*prev)
100 *prev = thunk->next;
101 HeapFree( GetProcessHeap(), 0, thunk );
102 return;
105 fprintf( stderr, "THUNK_Free: invalid thunk addr %p\n", thunk );
109 /***********************************************************************
110 * THUNK_CallWndProc16
112 * Call a 16-bit window procedure
114 static LRESULT THUNK_CallWndProc16( WNDPROC16 proc, HWND16 hwnd, UINT16 msg,
115 WPARAM16 wParam, LPARAM lParam )
117 if ((msg == WM_CREATE) || (msg == WM_NCCREATE))
119 CREATESTRUCT16 *cs = (CREATESTRUCT16 *)PTR_SEG_TO_LIN(lParam);
120 /* Build the CREATESTRUCT on the 16-bit stack. */
121 /* This is really ugly, but some programs (notably the */
122 /* "Undocumented Windows" examples) want it that way. */
123 return CallTo16_long_lllllllwlwwwl( (FARPROC16)proc,
124 cs->dwExStyle, cs->lpszClass, cs->lpszName, cs->style,
125 MAKELONG( cs->y, cs->x ), MAKELONG( cs->cy, cs->cx ),
126 MAKELONG( cs->hMenu, cs->hwndParent ), cs->hInstance,
127 (LONG)cs->lpCreateParams, hwnd, msg, wParam,
128 MAKELONG( IF1632_Saved16_sp-sizeof(CREATESTRUCT16),
129 IF1632_Saved16_ss ) );
131 return CallTo16_long_wwwl( (FARPROC16)proc, hwnd, msg, wParam, lParam );
135 /***********************************************************************
136 * THUNK_EnumObjects16 (GDI.71)
138 INT16 THUNK_EnumObjects16( HDC16 hdc, INT16 nObjType,
139 GOBJENUMPROC16 func, LPARAM lParam )
141 DECL_THUNK( thunk, func, CallTo16_word_ll );
142 return EnumObjects16( hdc, nObjType, (GOBJENUMPROC16)&thunk, lParam );
146 /***********************************************************************
147 * THUNK_EnumObjects32 (GDI32.89)
149 INT32 THUNK_EnumObjects32( HDC32 hdc, INT32 nObjType,
150 GOBJENUMPROC32 func, LPARAM lParam )
152 DECL_THUNK( thunk, func, CallTo32_2 );
153 return EnumObjects32( hdc, nObjType, (GOBJENUMPROC32)&thunk, lParam );
157 /*************************************************************************
158 * THUNK_EnumFonts16 (GDI.70)
160 INT16 THUNK_EnumFonts16( HDC16 hdc, LPCSTR lpFaceName,
161 FONTENUMPROC16 func, LPARAM lParam )
163 DECL_THUNK( thunk, func, CallTo16_word_llwl );
164 return EnumFonts16( hdc, lpFaceName, (FONTENUMPROC16)&thunk, lParam );
167 /*************************************************************************
168 * THUNK_EnumFonts32A (GDI32.84)
170 INT32 THUNK_EnumFonts32A( HDC32 hdc, LPCSTR lpFaceName,
171 FONTENUMPROC32A func, LPARAM lParam )
173 DECL_THUNK( thunk, func, CallTo32_4 );
174 return EnumFonts32A( hdc, lpFaceName, (FONTENUMPROC32A)&thunk, lParam );
177 /*************************************************************************
178 * THUNK_EnumFonts32W (GDI32.85)
180 INT32 THUNK_EnumFonts32W( HDC32 hdc, LPCWSTR lpFaceName,
181 FONTENUMPROC32W func, LPARAM lParam )
183 DECL_THUNK( thunk, func, CallTo32_4 );
184 return EnumFonts32W( hdc, lpFaceName, (FONTENUMPROC32W)&thunk, lParam );
187 /******************************************************************
188 * THUNK_EnumMetaFile16 (GDI.175)
190 BOOL16 THUNK_EnumMetaFile16( HDC16 hdc, HMETAFILE16 hmf,
191 MFENUMPROC16 func, LPARAM lParam )
193 DECL_THUNK( thunk, func, CallTo16_word_wllwl );
194 return EnumMetaFile16( hdc, hmf, (MFENUMPROC16)&thunk, lParam );
198 /*************************************************************************
199 * THUNK_EnumFontFamilies16 (GDI.330)
201 INT16 THUNK_EnumFontFamilies16( HDC16 hdc, LPCSTR lpszFamily,
202 FONTENUMPROC16 func, LPARAM lParam )
204 DECL_THUNK( thunk, func, CallTo16_word_llwl );
205 return EnumFontFamilies16(hdc, lpszFamily, (FONTENUMPROC16)&thunk, lParam);
209 /*************************************************************************
210 * THUNK_EnumFontFamilies32A (GDI32.80)
212 INT32 THUNK_EnumFontFamilies32A( HDC32 hdc, LPCSTR lpszFamily,
213 FONTENUMPROC32A func, LPARAM lParam )
215 DECL_THUNK( thunk, func, CallTo32_4 );
216 return EnumFontFamilies32A(hdc,lpszFamily,(FONTENUMPROC32A)&thunk,lParam);
220 /*************************************************************************
221 * THUNK_EnumFontFamilies32W (GDI32.83)
223 INT32 THUNK_EnumFontFamilies32W( HDC32 hdc, LPCWSTR lpszFamily,
224 FONTENUMPROC32W func, LPARAM lParam )
226 DECL_THUNK( thunk, func, CallTo32_4 );
227 return EnumFontFamilies32W(hdc,lpszFamily,(FONTENUMPROC32W)&thunk,lParam);
230 /*************************************************************************
231 * THUNK_EnumFontFamiliesEx16 (GDI.613)
233 INT16 THUNK_EnumFontFamiliesEx16( HDC16 hdc, LPLOGFONT16 lpLF,
234 FONTENUMPROCEX16 func, LPARAM lParam,
235 DWORD reserved )
237 DECL_THUNK( thunk, func, CallTo16_word_llwl );
238 return EnumFontFamiliesEx16( hdc, lpLF, (FONTENUMPROCEX16)&thunk,
239 lParam, reserved );
243 /*************************************************************************
244 * THUNK_EnumFontFamiliesEx32A (GDI32.81)
246 INT32 THUNK_EnumFontFamiliesEx32A( HDC32 hdc, LPLOGFONT32A lpLF,
247 FONTENUMPROCEX32A func, LPARAM lParam,
248 DWORD reserved)
250 DECL_THUNK( thunk, func, CallTo32_4 );
251 return EnumFontFamiliesEx32A( hdc, lpLF, (FONTENUMPROCEX32A)&thunk,
252 lParam, reserved );
256 /*************************************************************************
257 * THUNK_EnumFontFamiliesEx32W (GDI32.82)
259 INT32 THUNK_EnumFontFamiliesEx32W( HDC32 hdc, LPLOGFONT32W lpLF,
260 FONTENUMPROCEX32W func, LPARAM lParam,
261 DWORD reserved )
263 DECL_THUNK( thunk, func, CallTo32_4 );
264 return EnumFontFamiliesEx32W( hdc, lpLF, (FONTENUMPROCEX32W)&thunk,
265 lParam, reserved );
269 /**********************************************************************
270 * THUNK_LineDDA16 (GDI.100)
272 void THUNK_LineDDA16( INT16 nXStart, INT16 nYStart, INT16 nXEnd, INT16 nYEnd,
273 LINEDDAPROC16 func, LPARAM lParam )
275 DECL_THUNK( thunk, func, CallTo16_word_wwl );
276 LineDDA16( nXStart, nYStart, nXEnd, nYEnd, (LINEDDAPROC16)&thunk, lParam );
280 /**********************************************************************
281 * THUNK_LineDDA32 (GDI32.248)
283 BOOL32 THUNK_LineDDA32( INT32 nXStart, INT32 nYStart, INT32 nXEnd, INT32 nYEnd,
284 LINEDDAPROC32 func, LPARAM lParam )
286 DECL_THUNK( thunk, func, CallTo32_3 );
287 return LineDDA32( nXStart, nYStart, nXEnd, nYEnd,
288 (LINEDDAPROC32)&thunk, lParam );
292 /*******************************************************************
293 * THUNK_EnumWindows16 (USER.54)
295 BOOL16 THUNK_EnumWindows16( WNDENUMPROC16 func, LPARAM lParam )
297 DECL_THUNK( thunk, func, CallTo16_word_wl );
298 return EnumWindows16( (WNDENUMPROC16)&thunk, lParam );
302 /*******************************************************************
303 * THUNK_EnumWindows32 (USER32.192)
305 BOOL32 THUNK_EnumWindows32( WNDENUMPROC32 func, LPARAM lParam )
307 DECL_THUNK( thunk, func, CallTo32_2 );
308 return EnumWindows32( (WNDENUMPROC32)&thunk, lParam );
312 /**********************************************************************
313 * THUNK_EnumChildWindows16 (USER.55)
315 BOOL16 THUNK_EnumChildWindows16( HWND16 parent, WNDENUMPROC16 func,
316 LPARAM lParam )
318 DECL_THUNK( thunk, func, CallTo16_word_wl );
319 return EnumChildWindows16( parent, (WNDENUMPROC16)&thunk, lParam );
323 /**********************************************************************
324 * THUNK_EnumChildWindows32 (USER32.177)
326 BOOL32 THUNK_EnumChildWindows32( HWND32 parent, WNDENUMPROC32 func,
327 LPARAM lParam )
329 DECL_THUNK( thunk, func, CallTo32_2 );
330 return EnumChildWindows32( parent, (WNDENUMPROC32)&thunk, lParam );
334 /**********************************************************************
335 * THUNK_EnumTaskWindows16 (USER.225)
337 BOOL16 THUNK_EnumTaskWindows16( HTASK16 hTask, WNDENUMPROC16 func,
338 LPARAM lParam )
340 DECL_THUNK( thunk, func, CallTo16_word_wl );
341 return EnumTaskWindows16( hTask, (WNDENUMPROC16)&thunk, lParam );
345 /**********************************************************************
346 * THUNK_EnumThreadWindows (USER32.189)
348 BOOL32 THUNK_EnumThreadWindows( DWORD id, WNDENUMPROC32 func, LPARAM lParam )
350 DECL_THUNK( thunk, func, CallTo32_2 );
351 return EnumThreadWindows( id, (WNDENUMPROC32)&thunk, lParam );
355 /***********************************************************************
356 * THUNK_EnumProps16 (USER.27)
358 INT16 THUNK_EnumProps16( HWND16 hwnd, PROPENUMPROC16 func )
360 DECL_THUNK( thunk, func, CallTo16_word_wlw );
361 return EnumProps16( hwnd, (PROPENUMPROC16)&thunk );
365 /***********************************************************************
366 * THUNK_EnumProps32A (USER32.185)
368 INT32 THUNK_EnumProps32A( HWND32 hwnd, PROPENUMPROC32A func )
370 DECL_THUNK( thunk, func, CallTo32_3 );
371 return EnumProps32A( hwnd, (PROPENUMPROC32A)&thunk );
375 /***********************************************************************
376 * THUNK_EnumProps32W (USER32.188)
378 INT32 THUNK_EnumProps32W( HWND32 hwnd, PROPENUMPROC32W func )
380 DECL_THUNK( thunk, func, CallTo32_3 );
381 return EnumProps32W( hwnd, (PROPENUMPROC32W)&thunk );
385 /***********************************************************************
386 * THUNK_EnumPropsEx32A (USER32.186)
388 INT32 THUNK_EnumPropsEx32A( HWND32 hwnd, PROPENUMPROCEX32A func, LPARAM lParam)
390 DECL_THUNK( thunk, func, CallTo32_4 );
391 return EnumPropsEx32A( hwnd, (PROPENUMPROCEX32A)&thunk, lParam );
395 /***********************************************************************
396 * THUNK_EnumPropsEx32W (USER32.187)
398 INT32 THUNK_EnumPropsEx32W( HWND32 hwnd, PROPENUMPROCEX32W func, LPARAM lParam)
400 DECL_THUNK( thunk, func, CallTo32_4 );
401 return EnumPropsEx32W( hwnd, (PROPENUMPROCEX32W)&thunk, lParam );
405 /***********************************************************************
406 * THUNK_EnumSystemCodePages32A (KERNEL32.92)
408 BOOL32 THUNK_EnumSystemCodePages32A( CODEPAGE_ENUMPROC32A func, DWORD flags )
410 DECL_THUNK( thunk, func, CallTo32_1 );
411 return EnumSystemCodePages32A( (CODEPAGE_ENUMPROC32A)&thunk, flags );
415 /***********************************************************************
416 * THUNK_EnumSystemCodePages32W (KERNEL32.93)
418 BOOL32 THUNK_EnumSystemCodePages32W( CODEPAGE_ENUMPROC32W func, DWORD flags )
420 DECL_THUNK( thunk, func, CallTo32_1 );
421 return EnumSystemCodePages32W( (CODEPAGE_ENUMPROC32W)&thunk, flags );
424 /***********************************************************************
425 * THUNK_EnumSystemLocales32A (KERNEL32.92)
427 BOOL32 THUNK_EnumSystemLocales32A( LOCALE_ENUMPROC32A func, DWORD flags )
429 DECL_THUNK( thunk, func, CallTo32_1 );
430 return EnumSystemLocales32A( (LOCALE_ENUMPROC32A)&thunk, flags );
434 /***********************************************************************
435 * THUNK_EnumSystemLocales32W (KERNEL32.93)
437 BOOL32 THUNK_EnumSystemLocales32W( LOCALE_ENUMPROC32W func, DWORD flags )
439 DECL_THUNK( thunk, func, CallTo32_1 );
440 return EnumSystemLocales32W( (LOCALE_ENUMPROC32W)&thunk, flags );
443 /***********************************************************************
444 * THUNK_EnumResourceLanguages32W (KERNEL32.87)
446 BOOL32 THUNK_EnumResourceLanguages32W( HMODULE32 hmod,LPCWSTR type,LPCWSTR name,ENUMRESLANGPROC32W func, LONG lParam )
448 DECL_THUNK( thunk, func, CallTo32_5 );
449 return EnumResourceLanguages32W( hmod,type,name,(ENUMRESLANGPROC32W)&thunk, lParam );
452 /***********************************************************************
453 * THUNK_EnumResourceLanguages32A (KERNEL32.86)
455 BOOL32 THUNK_EnumResourceLanguages32A( HMODULE32 hmod,LPCSTR type,LPCSTR name,ENUMRESLANGPROC32A func, LONG lParam )
457 DECL_THUNK( thunk, func, CallTo32_5 );
458 return EnumResourceLanguages32A( hmod,type,name,(ENUMRESLANGPROC32A)&thunk, lParam );
461 /***********************************************************************
462 * THUNK_EnumResourceNames32A (KERNEL32.88)
464 BOOL32 THUNK_EnumResourceNames32A( HMODULE32 hmod, LPCSTR type,
465 ENUMRESNAMEPROC32A func, LONG lParam )
467 DECL_THUNK( thunk, func, CallTo32_4 );
468 return EnumResourceNames32A( hmod,type,(ENUMRESNAMEPROC32A)&thunk,lParam );
471 /***********************************************************************
472 * THUNK_EnumResourceNames32W (KERNEL32.89)
474 BOOL32 THUNK_EnumResourceNames32W( HMODULE32 hmod, LPCWSTR type,
475 ENUMRESNAMEPROC32W func, LONG lParam )
477 DECL_THUNK( thunk, func, CallTo32_4 );
478 return EnumResourceNames32W( hmod,type,(ENUMRESNAMEPROC32W)&thunk, lParam);
481 /***********************************************************************
482 * THUNK_EnumResourceTypes32A (KERNEL32.90)
484 BOOL32 THUNK_EnumResourceTypes32A( HMODULE32 hmod,ENUMRESTYPEPROC32A func, LONG lParam )
486 DECL_THUNK( thunk, func, CallTo32_3 );
487 return EnumResourceTypes32A( hmod,(ENUMRESTYPEPROC32A)&thunk, lParam );
490 /***********************************************************************
491 * THUNK_EnumResourceTypes32W (KERNEL32.91)
493 BOOL32 THUNK_EnumResourceTypes32W( HMODULE32 hmod,ENUMRESTYPEPROC32W func, LONG lParam )
495 DECL_THUNK( thunk, func, CallTo32_3 );
496 return EnumResourceTypes32W( hmod,(ENUMRESTYPEPROC32W)&thunk, lParam );
500 /***********************************************************************
501 * THUNK_GrayString16 (USER.185)
503 BOOL16 THUNK_GrayString16( HDC16 hdc, HBRUSH16 hbr, GRAYSTRINGPROC16 func,
504 LPARAM lParam, INT16 cch, INT16 x, INT16 y,
505 INT16 cx, INT16 cy )
507 DECL_THUNK( thunk, func, CallTo16_word_wlw );
508 if (!func)
509 return GrayString16( hdc, hbr, NULL, lParam, cch, x, y, cx, cy );
510 else
511 return GrayString16( hdc, hbr, (GRAYSTRINGPROC16)&thunk, lParam, cch,
512 x, y, cx, cy );
516 /***********************************************************************
517 * THUNK_GrayString32A (USER32.314)
519 BOOL32 THUNK_GrayString32A( HDC32 hdc, HBRUSH32 hbr, GRAYSTRINGPROC32 func,
520 LPARAM lParam, INT32 cch, INT32 x, INT32 y,
521 INT32 cx, INT32 cy )
523 DECL_THUNK( thunk, func, CallTo32_3 );
524 if (!func)
525 return GrayString32A( hdc, hbr, NULL, lParam, cch, x, y, cx, cy );
526 else
527 return GrayString32A( hdc, hbr, (GRAYSTRINGPROC32)&thunk, lParam, cch,
528 x, y, cx, cy );
532 /***********************************************************************
533 * THUNK_GrayString32W (USER32.315)
535 BOOL32 THUNK_GrayString32W( HDC32 hdc, HBRUSH32 hbr, GRAYSTRINGPROC32 func,
536 LPARAM lParam, INT32 cch, INT32 x, INT32 y,
537 INT32 cx, INT32 cy )
539 DECL_THUNK( thunk, func, CallTo32_3 );
540 if (!func)
541 return GrayString32W( hdc, hbr, NULL, lParam, cch, x, y, cx, cy );
542 else
543 return GrayString32W( hdc, hbr, (GRAYSTRINGPROC32)&thunk, lParam, cch,
544 x, y, cx, cy );
548 /***********************************************************************
549 * THUNK_SetWindowsHook16 (USER.121)
551 FARPROC16 THUNK_SetWindowsHook16( INT16 id, HOOKPROC16 proc )
553 HINSTANCE16 hInst = FarGetOwner( HIWORD(proc) );
554 HTASK16 hTask = (id == WH_MSGFILTER) ? GetCurrentTask() : 0;
555 THUNK *thunk = THUNK_Alloc( (FARPROC16)proc, (RELAY)CallTo16_long_wwl );
556 if (!thunk) return 0;
557 return (FARPROC16)SetWindowsHookEx16( id, (HOOKPROC16)thunk, hInst, hTask);
561 /***********************************************************************
562 * THUNK_UnhookWindowsHook16 (USER.234)
564 BOOL16 THUNK_UnhookWindowsHook16( INT16 id, HOOKPROC16 proc )
566 BOOL16 ret;
567 THUNK *thunk = THUNK_Find( (FARPROC16)proc );
568 if (!thunk) return FALSE;
569 ret = UnhookWindowsHook16( id, (HOOKPROC16)thunk );
570 THUNK_Free( thunk );
571 return ret;
575 /***********************************************************************
576 * THUNK_SetWindowsHookEx16 (USER.291)
578 HHOOK THUNK_SetWindowsHookEx16( INT16 id, HOOKPROC16 proc, HINSTANCE16 hInst,
579 HTASK16 hTask )
581 THUNK *thunk = THUNK_Alloc( (FARPROC16)proc, (RELAY)CallTo16_long_wwl );
582 if (!thunk) return 0;
583 return SetWindowsHookEx16( id, (HOOKPROC16)thunk, hInst, hTask );
587 /***********************************************************************
588 * THUNK_UnhookWindowHookEx16 (USER.292)
590 BOOL16 THUNK_UnhookWindowsHookEx16( HHOOK hhook )
592 THUNK *thunk = (THUNK *)HOOK_GetProc16( hhook );
593 BOOL16 ret = UnhookWindowsHookEx16( hhook );
594 if (thunk) THUNK_Free( thunk );
595 return ret;
599 /*************************************************************
600 * THUNK_SetUnhandledExceptionFilter (KERNEL32.516)
602 LPTOP_LEVEL_EXCEPTION_FILTER THUNK_SetUnhandledExceptionFilter(
603 LPTOP_LEVEL_EXCEPTION_FILTER filter )
605 LPTOP_LEVEL_EXCEPTION_FILTER old;
606 THUNK *thunk = THUNK_Alloc( (FARPROC16)filter, (RELAY)CallTo32_1 );
607 if (!thunk) return NULL;
608 old = SetUnhandledExceptionFilter( (LPTOP_LEVEL_EXCEPTION_FILTER)thunk );
609 if (!old) return NULL;
610 thunk = (THUNK *)old;
611 old = (LPTOP_LEVEL_EXCEPTION_FILTER)thunk->proc;
612 THUNK_Free( thunk );
613 return old;
617 static FARPROC16 defDCHookProc = NULL;
619 /***********************************************************************
620 * THUNK_SetDCHook (GDI.190)
622 BOOL16 THUNK_SetDCHook( HDC16 hdc, FARPROC16 proc, DWORD dwHookData )
624 THUNK *thunk, *oldThunk;
626 if (!defDCHookProc) /* Get DCHook Win16 entry point */
627 defDCHookProc = MODULE_GetEntryPoint( GetModuleHandle16("USER"), 362 );
629 if (proc != defDCHookProc)
631 thunk = THUNK_Alloc( proc, (RELAY)CallTo16_word_wwll );
632 if (!thunk) return FALSE;
634 else thunk = (THUNK *)DCHook;
636 /* Free the previous thunk */
637 GetDCHook( hdc, (FARPROC16 *)&oldThunk );
638 if (oldThunk && (oldThunk != (THUNK *)DCHook)) THUNK_Free( oldThunk );
640 return SetDCHook( hdc, (FARPROC16)thunk, dwHookData );
644 /***********************************************************************
645 * THUNK_GetDCHook (GDI.191)
647 DWORD THUNK_GetDCHook( HDC16 hdc, FARPROC16 *phookProc )
649 THUNK *thunk = NULL;
650 DWORD ret = GetDCHook( hdc, (FARPROC16 *)&thunk );
651 if (thunk)
653 if (thunk == (THUNK *)DCHook)
655 if (!defDCHookProc) /* Get DCHook Win16 entry point */
656 defDCHookProc = MODULE_GetEntryPoint(GetModuleHandle16("USER"),
657 362 );
658 *phookProc = defDCHookProc;
660 else *phookProc = thunk->proc;
662 return ret;
666 struct thunkstruct
668 char magic[4];
669 DWORD x1;
670 DWORD x2;
673 UINT32 ThunkConnect32( struct thunkstruct *ths, LPSTR thunkfun16,
674 LPSTR module16, LPSTR module32, HMODULE32 hmod32,
675 DWORD dllinitarg1 )
677 HINSTANCE16 hmm;
679 fprintf(stdnimp,"ThunkConnect32(<struct>,%s,%s,%s,%x,%lx)\n",
680 thunkfun16,module32,module16,hmod32,dllinitarg1
682 fprintf(stdnimp," magic = %c%c%c%c\n",
683 ths->magic[0],
684 ths->magic[1],
685 ths->magic[2],
686 ths->magic[3]
688 fprintf(stdnimp," x1 = %lx\n",ths->x1);
689 fprintf(stdnimp," x2 = %lx\n",ths->x2);
690 hmm=LoadModule16(module16,NULL);
691 return TRUE;