Made register and interrupt flags instead of entry point types, so

that we can have both stdcall and cdecl register functions.
Changed 16-bit .spec.c file generation to avoid including builtin16.h.
This commit is contained in:
Alexandre Julliard 2001-12-14 23:14:22 +00:00
parent 99ed342df0
commit 7662ea1004
18 changed files with 627 additions and 584 deletions

View file

@ -228,9 +228,9 @@ $(SUBDIRS:%=%/__uninstall__): dummy
# Misc. rules
$(SPEC_SRCS:.spec=.spec.c): $(WINEBUILD) $(TOPSRCDIR)/include/builtin16.h
$(SPEC_SRCS:.spec=.spec.c): $(WINEBUILD)
$(GLUE:.c=.glue.c): $(WINEBUILD) $(TOPSRCDIR)/include/builtin16.h
$(GLUE:.c=.glue.c): $(WINEBUILD)
$(RC_SRCS:.rc=.res): $(WRC)

View file

@ -61,8 +61,8 @@ rsrc version16.res
52 pascal16 FreeProcInstance(segptr) FreeProcInstance16
53 stub CallProcInstance
54 pascal16 GetInstanceData(word word word) GetInstanceData16
55 register Catch(ptr) Catch16
56 register Throw(ptr word) Throw16
55 pascal -register Catch(ptr) Catch16
56 pascal -register Throw(ptr word) Throw16
57 pascal16 GetProfileInt(str str s_word) GetProfileInt16
58 pascal16 GetProfileString(str str str ptr word) GetProfileString16
59 pascal16 WriteProfileString(str str str) WriteProfileString16
@ -98,7 +98,7 @@ rsrc version16.res
88 pascal lstrcpy(segptr str) lstrcpy16
89 pascal lstrcat(segstr str) lstrcat16
90 pascal16 lstrlen(str) lstrlen16
91 register InitTask() InitTask16
91 pascal -register InitTask() InitTask16
92 pascal GetTempDrive(word) GetTempDrive
93 pascal16 GetCodeHandle(segptr) GetCodeHandle16
94 pascal16 DefineHandleTable(word) DefineHandleTable16
@ -109,14 +109,14 @@ rsrc version16.res
99 stub GetLPErrMode
100 pascal16 ValidateCodeSegments() KERNEL_nop
101 stub NoHookDosCall
102 register DOS3Call() DOS3Call
103 register NetBIOSCall() NetBIOSCall16
102 pascal -register DOS3Call() DOS3Call
103 pascal -register NetBIOSCall() NetBIOSCall16
104 pascal16 GetCodeInfo(segptr ptr) GetCodeInfo16
105 pascal16 GetExeVersion() GetExeVersion16
106 pascal SetSwapAreaSize(word) SetSwapAreaSize16
107 pascal16 SetErrorMode(word) SetErrorMode16
108 pascal16 SwitchStackTo(word word word) SwitchStackTo16 # STO in W2.0
109 register SwitchStackBack() SwitchStackBack16 # SBACK in W2.0
109 pascal -register SwitchStackBack() SwitchStackBack16 # SBACK in W2.0
110 pascal PatchCodeHandle(word) PatchCodeHandle16
111 pascal GlobalWire(word) GlobalWire16
112 pascal16 GlobalUnWire(word) GlobalUnWire16
@ -211,7 +211,7 @@ rsrc version16.res
200 pascal16 ValidateFreeSpaces() KERNEL_nop
201 stub ReplaceInst
202 stub RegisterPtrace
203 register DebugBreak() DebugBreak16
203 pascal -register DebugBreak() DebugBreak16
204 stub SwapRecording
205 stub CVWBreak
206 pascal16 AllocSelectorArray(word) AllocSelectorArray16
@ -274,7 +274,7 @@ rsrc version16.res
324 pascal16 LogError(word ptr) LogError16
325 pascal16 LogParamError(word ptr ptr) LogParamError16
326 pascal16 IsRomFile(word) IsRomFile16
327 register K327() HandleParamError
327 pascal -register K327() HandleParamError
328 pascal16 _DebugOutput() _DebugOutput
329 pascal16 K329(str word) DebugFillBuffer
332 variable THHOOK(0 0 0 0 0 0 0 0)
@ -313,7 +313,7 @@ rsrc version16.res
360 pascal16 OpenFileEx(str ptr word) OpenFile16
361 pascal16 PIGLET_361() KERNEL_nop
362 stub ThunkTerminateProcess
365 register GlobalChangeLockCount(word word) GlobalChangeLockCount16
365 pascal -register GlobalChangeLockCount(word word) GlobalChangeLockCount16
# 403-404 are common to all versions
@ -382,8 +382,8 @@ rsrc version16.res
469 stub WOAGimmeTitle
470 stub WOADestroyConsole
471 pascal GetCurrentProcessId() GetCurrentProcessId
472 register MapHInstLS() MapHInstLS
473 register MapHInstSL() MapHInstSL
472 pascal -register MapHInstLS() MapHInstLS
473 pascal -register MapHInstSL() MapHInstSL
474 pascal CloseW32Handle(long) CloseHandle
475 pascal16 GetTEBSelectorFS() GetTEBSelectorFS16
476 pascal ConvertToGlobalHandle(long) ConvertToGlobalHandle
@ -482,7 +482,7 @@ rsrc version16.res
601 stub FreeCodeAlias
602 pascal16 GetDummyModuleHandleDS() GetDummyModuleHandleDS16
603 stub KERNEL_603 # OutputDebugString (?)
604 register CBClientGlueSL() CBClientGlueSL
604 pascal -register CBClientGlueSL() CBClientGlueSL
# FIXME: 605 is duplicate of 562
605 pascal AllocSLThunkletCallback_dup(long long) AllocSLThunkletCallback16
# FIXME: 606 is duplicate of 561
@ -502,16 +502,16 @@ rsrc version16.res
617 pascal16 GetMenu32Size(ptr) GetMenu32Size16
618 pascal16 GetDialog32Size(ptr) GetDialog32Size16
619 pascal16 RegisterCBClient(word segptr long) RegisterCBClient16
620 register CBClientThunkSL() CBClientThunkSL
621 register CBClientThunkSLEx() CBClientThunkSLEx
620 pascal -register CBClientThunkSL() CBClientThunkSL
621 pascal -register CBClientThunkSLEx() CBClientThunkSLEx
622 pascal16 UnRegisterCBClient(word segptr long) UnRegisterCBClient16
623 pascal16 InitCBClient(long) InitCBClient16
624 pascal SetFastQueue(long long) SetFastQueue16
625 pascal GetFastQueue() GetFastQueue16
626 stub SmashEnvironment
627 pascal16 IsBadFlatReadWritePtr(segptr long word) IsBadFlatReadWritePtr16
630 register C16ThkSL() C16ThkSL
631 register C16ThkSL01() C16ThkSL01
630 pascal -register C16ThkSL() C16ThkSL
631 pascal -register C16ThkSL01() C16ThkSL01
651 pascal ThunkConnect16(str str word long ptr str word) ThunkConnect16
652 stub IsThreadId
653 stub OkWithKernelToChangeUsers
@ -529,7 +529,7 @@ rsrc version16.res
701 stub SSOnBigStack
702 stub SSCall
703 stub CallProc32WFix
704 register SSConfirmSmallStack() SSConfirmSmallStack
704 pascal -register SSConfirmSmallStack() SSConfirmSmallStack
# Win95 krnl386.exe also exports ordinals 802-864,

View file

@ -17,15 +17,15 @@ debug_channels (comm debugstr dll int resource stress thunk toolhelp win32)
# - code generated by the MS Thunk Compiler
# - symbols exported by the Oct 94 beta version of kernel32.dll
1 register -i386 VxDCall0(long) VxDCall
2 register -i386 VxDCall1(long) VxDCall
3 register -i386 VxDCall2(long) VxDCall
4 register -i386 VxDCall3(long) VxDCall
5 register -i386 VxDCall4(long) VxDCall
6 register -i386 VxDCall5(long) VxDCall
7 register -i386 VxDCall6(long) VxDCall
8 register -i386 VxDCall7(long) VxDCall
9 register -i386 VxDCall8(long) VxDCall
1 stdcall -register -i386 VxDCall0(long) VxDCall
2 stdcall -register -i386 VxDCall1(long) VxDCall
3 stdcall -register -i386 VxDCall2(long) VxDCall
4 stdcall -register -i386 VxDCall3(long) VxDCall
5 stdcall -register -i386 VxDCall4(long) VxDCall
6 stdcall -register -i386 VxDCall5(long) VxDCall
7 stdcall -register -i386 VxDCall6(long) VxDCall
8 stdcall -register -i386 VxDCall7(long) VxDCall
9 stdcall -register -i386 VxDCall8(long) VxDCall
10 stdcall k32CharToOemA(str ptr) k32CharToOemA
11 stdcall k32CharToOemBuffA(str ptr long) k32CharToOemBuffA
12 stdcall k32OemToCharA(ptr ptr) k32OemToCharA
@ -33,7 +33,7 @@ debug_channels (comm debugstr dll int resource stress thunk toolhelp win32)
14 stdcall k32LoadStringA(long long ptr long) k32LoadStringA
15 varargs k32wsprintfA(str str) k32wsprintfA
16 stdcall k32wvsprintfA(ptr str ptr) k32wvsprintfA
17 register -i386 CommonUnimpStub() CommonUnimpStub
17 stdcall -register -i386 CommonUnimpStub() CommonUnimpStub
18 stdcall GetProcessDword(long long) GetProcessDword
19 stub ThunkTheTemplateHandle
20 stdcall DosFileHandleToWin32Handle(long) DosFileHandleToWin32Handle
@ -54,20 +54,20 @@ debug_channels (comm debugstr dll int resource stress thunk toolhelp win32)
35 stdcall LoadLibrary16(str) LoadLibrary16
36 stdcall FreeLibrary16(long) FreeLibrary16
37 stdcall GetProcAddress16(long str) WIN32_GetProcAddress16
38 register -i386 AllocMappedBuffer() AllocMappedBuffer
39 register -i386 FreeMappedBuffer() FreeMappedBuffer
40 register -i386 OT_32ThkLSF() OT_32ThkLSF
38 stdcall -register -i386 AllocMappedBuffer() AllocMappedBuffer
39 stdcall -register -i386 FreeMappedBuffer() FreeMappedBuffer
40 stdcall -register -i386 OT_32ThkLSF() OT_32ThkLSF
41 stdcall ThunkInitLSF(long str long str str) ThunkInitLSF
42 register -i386 LogApiThkLSF(str) LogApiThkLSF
42 stdcall -register -i386 LogApiThkLSF(str) LogApiThkLSF
43 stdcall ThunkInitLS(long str long str str) ThunkInitLS
44 register -i386 LogApiThkSL(str) LogApiThkSL
45 register -i386 Common32ThkLS() Common32ThkLS
44 stdcall -register -i386 LogApiThkSL(str) LogApiThkSL
45 stdcall -register -i386 Common32ThkLS() Common32ThkLS
46 stdcall ThunkInitSL(long str long str str) ThunkInitSL
47 register -i386 LogCBThkSL(str) LogCBThkSL
47 stdcall -register -i386 LogCBThkSL(str) LogCBThkSL
48 stdcall ReleaseThunkLock(ptr) ReleaseThunkLock
49 stdcall RestoreThunkLock(long) RestoreThunkLock
51 register -i386 W32S_BackTo32() W32S_BackTo32
51 stdcall -register -i386 W32S_BackTo32() W32S_BackTo32
52 stdcall GetThunkBuff() GetThunkBuff
53 stdcall GetThunkStuff(str str) GetThunkStuff
54 stdcall K32WOWCallback16(long long) K32WOWCallback16
@ -105,8 +105,8 @@ debug_channels (comm debugstr dll int resource stress thunk toolhelp win32)
86 stdcall @(ptr) _KERNEL32_86
87 stdcall SSOnBigStack() SSOnBigStack
88 varargs SSCall(long long ptr) SSCall
89 register -i386 FT_PrologPrime() FT_PrologPrime
90 register -i386 QT_ThunkPrime() QT_ThunkPrime
89 stdcall -register -i386 FT_PrologPrime() FT_PrologPrime
90 stdcall -register -i386 QT_ThunkPrime() QT_ThunkPrime
91 stdcall PK16FNF(ptr) PK16FNF
92 stdcall GetPK16SysVar() GetPK16SysVar
93 stdcall GetpWin16Lock(ptr) GetpWin16Lock
@ -259,23 +259,23 @@ debug_channels (comm debugstr dll int resource stress thunk toolhelp win32)
@ stdcall ExitThread(long) ExitThread
@ stdcall ExpandEnvironmentStringsA(str ptr long) ExpandEnvironmentStringsA
@ stdcall ExpandEnvironmentStringsW(wstr ptr long) ExpandEnvironmentStringsW
@ register -i386 FT_Exit0() FT_Exit0
@ register -i386 FT_Exit12() FT_Exit12
@ register -i386 FT_Exit16() FT_Exit16
@ register -i386 FT_Exit20() FT_Exit20
@ register -i386 FT_Exit24() FT_Exit24
@ register -i386 FT_Exit28() FT_Exit28
@ register -i386 FT_Exit32() FT_Exit32
@ register -i386 FT_Exit36() FT_Exit36
@ register -i386 FT_Exit40() FT_Exit40
@ register -i386 FT_Exit44() FT_Exit44
@ register -i386 FT_Exit48() FT_Exit48
@ register -i386 FT_Exit4() FT_Exit4
@ register -i386 FT_Exit52() FT_Exit52
@ register -i386 FT_Exit56() FT_Exit56
@ register -i386 FT_Exit8() FT_Exit8
@ register -i386 FT_Prolog() FT_Prolog
@ register -i386 FT_Thunk() FT_Thunk
@ stdcall -register -i386 FT_Exit0() FT_Exit0
@ stdcall -register -i386 FT_Exit12() FT_Exit12
@ stdcall -register -i386 FT_Exit16() FT_Exit16
@ stdcall -register -i386 FT_Exit20() FT_Exit20
@ stdcall -register -i386 FT_Exit24() FT_Exit24
@ stdcall -register -i386 FT_Exit28() FT_Exit28
@ stdcall -register -i386 FT_Exit32() FT_Exit32
@ stdcall -register -i386 FT_Exit36() FT_Exit36
@ stdcall -register -i386 FT_Exit40() FT_Exit40
@ stdcall -register -i386 FT_Exit44() FT_Exit44
@ stdcall -register -i386 FT_Exit48() FT_Exit48
@ stdcall -register -i386 FT_Exit4() FT_Exit4
@ stdcall -register -i386 FT_Exit52() FT_Exit52
@ stdcall -register -i386 FT_Exit56() FT_Exit56
@ stdcall -register -i386 FT_Exit8() FT_Exit8
@ stdcall -register -i386 FT_Prolog() FT_Prolog
@ stdcall -register -i386 FT_Thunk() FT_Thunk
@ stdcall FatalAppExitA(long str) FatalAppExitA
@ stdcall FatalAppExitW(long wstr) FatalAppExitW
@ stub FatalExit
@ -531,8 +531,8 @@ debug_channels (comm debugstr dll int resource stress thunk toolhelp win32)
@ stub IsSLCallback
@ stdcall IsValidCodePage(long) IsValidCodePage
@ stdcall IsValidLocale(long long) IsValidLocale
@ register -i386 K32Thk1632Epilog() K32Thk1632Epilog
@ register -i386 K32Thk1632Prolog() K32Thk1632Prolog
@ stdcall -register -i386 K32Thk1632Epilog() K32Thk1632Epilog
@ stdcall -register -i386 K32Thk1632Prolog() K32Thk1632Prolog
@ stdcall LCMapStringA(long long str long ptr long) LCMapStringA
@ stdcall LCMapStringW(long long wstr long ptr long) LCMapStringW
@ forward LeaveCriticalSection ntdll.RtlLeaveCriticalSection
@ -557,10 +557,10 @@ debug_channels (comm debugstr dll int resource stress thunk toolhelp win32)
@ stdcall LockFileEx(long long long long long ptr) LockFileEx
@ stdcall LockResource(long) LockResource
@ stdcall MakeCriticalSectionGlobal(ptr) MakeCriticalSectionGlobal
@ register -i386 MapHInstLS() MapHInstLS
@ register -i386 MapHInstLS_PN() MapHInstLS_PN
@ register -i386 MapHInstSL() MapHInstSL
@ register -i386 MapHInstSL_PN() MapHInstSL_PN
@ stdcall -register -i386 MapHInstLS() MapHInstLS
@ stdcall -register -i386 MapHInstLS_PN() MapHInstLS_PN
@ stdcall -register -i386 MapHInstSL() MapHInstSL
@ stdcall -register -i386 MapHInstSL_PN() MapHInstSL_PN
@ stdcall MapHModuleLS(long) MapHModuleLS
@ stdcall MapHModuleSL(long) MapHModuleSL
@ stdcall MapLS(ptr) MapLS
@ -602,7 +602,7 @@ debug_channels (comm debugstr dll int resource stress thunk toolhelp win32)
@ stdcall Process32Next (ptr ptr) Process32Next
@ stdcall PulseEvent(long) PulseEvent
@ stdcall PurgeComm(long long) PurgeComm
@ register -i386 QT_Thunk() QT_Thunk
@ stdcall -register -i386 QT_Thunk() QT_Thunk
@ stdcall QueryDosDeviceA(str ptr long) QueryDosDeviceA
@ stdcall QueryDosDeviceW(wstr ptr long) QueryDosDeviceW
@ stub QueryNumberOfEventLogRecords
@ -635,26 +635,26 @@ debug_channels (comm debugstr dll int resource stress thunk toolhelp win32)
@ forward RtlMoveMemory NTDLL.RtlMoveMemory
@ forward RtlUnwind NTDLL.RtlUnwind
@ forward RtlZeroMemory NTDLL.RtlZeroMemory
@ register -i386 SMapLS() SMapLS
@ register -i386 SMapLS_IP_EBP_12() SMapLS_IP_EBP_12
@ register -i386 SMapLS_IP_EBP_16() SMapLS_IP_EBP_16
@ register -i386 SMapLS_IP_EBP_20() SMapLS_IP_EBP_20
@ register -i386 SMapLS_IP_EBP_24() SMapLS_IP_EBP_24
@ register -i386 SMapLS_IP_EBP_28() SMapLS_IP_EBP_28
@ register -i386 SMapLS_IP_EBP_32() SMapLS_IP_EBP_32
@ register -i386 SMapLS_IP_EBP_36() SMapLS_IP_EBP_36
@ register -i386 SMapLS_IP_EBP_40() SMapLS_IP_EBP_40
@ register -i386 SMapLS_IP_EBP_8() SMapLS_IP_EBP_8
@ register -i386 SUnMapLS() SUnMapLS
@ register -i386 SUnMapLS_IP_EBP_12() SUnMapLS_IP_EBP_12
@ register -i386 SUnMapLS_IP_EBP_16() SUnMapLS_IP_EBP_16
@ register -i386 SUnMapLS_IP_EBP_20() SUnMapLS_IP_EBP_20
@ register -i386 SUnMapLS_IP_EBP_24() SUnMapLS_IP_EBP_24
@ register -i386 SUnMapLS_IP_EBP_28() SUnMapLS_IP_EBP_28
@ register -i386 SUnMapLS_IP_EBP_32() SUnMapLS_IP_EBP_32
@ register -i386 SUnMapLS_IP_EBP_36() SUnMapLS_IP_EBP_36
@ register -i386 SUnMapLS_IP_EBP_40() SUnMapLS_IP_EBP_40
@ register -i386 SUnMapLS_IP_EBP_8() SUnMapLS_IP_EBP_8
@ stdcall -register -i386 SMapLS() SMapLS
@ stdcall -register -i386 SMapLS_IP_EBP_12() SMapLS_IP_EBP_12
@ stdcall -register -i386 SMapLS_IP_EBP_16() SMapLS_IP_EBP_16
@ stdcall -register -i386 SMapLS_IP_EBP_20() SMapLS_IP_EBP_20
@ stdcall -register -i386 SMapLS_IP_EBP_24() SMapLS_IP_EBP_24
@ stdcall -register -i386 SMapLS_IP_EBP_28() SMapLS_IP_EBP_28
@ stdcall -register -i386 SMapLS_IP_EBP_32() SMapLS_IP_EBP_32
@ stdcall -register -i386 SMapLS_IP_EBP_36() SMapLS_IP_EBP_36
@ stdcall -register -i386 SMapLS_IP_EBP_40() SMapLS_IP_EBP_40
@ stdcall -register -i386 SMapLS_IP_EBP_8() SMapLS_IP_EBP_8
@ stdcall -register -i386 SUnMapLS() SUnMapLS
@ stdcall -register -i386 SUnMapLS_IP_EBP_12() SUnMapLS_IP_EBP_12
@ stdcall -register -i386 SUnMapLS_IP_EBP_16() SUnMapLS_IP_EBP_16
@ stdcall -register -i386 SUnMapLS_IP_EBP_20() SUnMapLS_IP_EBP_20
@ stdcall -register -i386 SUnMapLS_IP_EBP_24() SUnMapLS_IP_EBP_24
@ stdcall -register -i386 SUnMapLS_IP_EBP_28() SUnMapLS_IP_EBP_28
@ stdcall -register -i386 SUnMapLS_IP_EBP_32() SUnMapLS_IP_EBP_32
@ stdcall -register -i386 SUnMapLS_IP_EBP_36() SUnMapLS_IP_EBP_36
@ stdcall -register -i386 SUnMapLS_IP_EBP_40() SUnMapLS_IP_EBP_40
@ stdcall -register -i386 SUnMapLS_IP_EBP_8() SUnMapLS_IP_EBP_8
@ stdcall ScrollConsoleScreenBufferA(long ptr ptr ptr ptr) ScrollConsoleScreenBufferA
@ stdcall ScrollConsoleScreenBufferW(long ptr ptr ptr ptr) ScrollConsoleScreenBufferW
@ stdcall SearchPathA(str str str long ptr ptr) SearchPathA
@ -744,7 +744,7 @@ debug_channels (comm debugstr dll int resource stress thunk toolhelp win32)
@ stdcall UTRegister(long str str str ptr ptr ptr) UTRegister
@ stdcall UTUnRegister(long) UTUnRegister
@ stdcall UnMapLS(long) UnMapLS
@ register -i386 UnMapSLFixArray(long long) UnMapSLFixArray
@ stdcall -register -i386 UnMapSLFixArray(long long) UnMapSLFixArray
@ stdcall UnhandledExceptionFilter(ptr) UnhandledExceptionFilter
@ stdcall UninitializeCriticalSection(ptr) UninitializeCriticalSection
@ stdcall UnlockFile(long long long long long) UnlockFile
@ -996,7 +996,6 @@ debug_channels (comm debugstr dll int resource stress thunk toolhelp win32)
@ varargs __wine_call_from_16_word() __wine_call_from_16_word
@ varargs __wine_call_from_16_long() __wine_call_from_16_long
@ varargs __wine_call_from_16_regs() __wine_call_from_16_regs
@ varargs __wine_call_from_16_thunk() __wine_call_from_16_thunk
@ stdcall wine_call_to_16_word(ptr long) wine_call_to_16_word
@ stdcall wine_call_to_16_long(ptr long) wine_call_to_16_long
@ stdcall wine_call_to_16_regs_short(ptr long) wine_call_to_16_regs_short

View file

@ -16,7 +16,6 @@
#include "winerror.h"
#include "wine/winbase16.h"
#include "builtin16.h"
#include "callback.h"
#include "debugtools.h"
#include "flatthunk.h"
@ -28,6 +27,11 @@
DEFAULT_DEBUG_CHANNEL(thunk);
#ifdef __i386__
extern void __wine_call_from_16_thunk();
#else
static void __wine_call_from_16_thunk() { }
#endif
/***********************************************************************
* *

View file

@ -2,7 +2,7 @@ name win87em
type win16
owner kernel32
1 register _fpMath() WIN87_fpmath
1 pascal -register _fpMath() WIN87_fpmath
3 pascal16 __WinEm87Info(ptr word) WIN87_WinEm87Info
4 pascal16 __WinEm87Restore(ptr word) WIN87_WinEm87Restore
5 pascal16 __WinEm87Save(ptr word) WIN87_WinEm87Save

View file

@ -4,4 +4,4 @@ owner kernel32
1 stub WINDEBUG
2 stub WEP
3 register WinNotify() WinNotify16
3 pascal -register WinNotify() WinNotify16

View file

@ -3,43 +3,43 @@ type win16
owner kernel32
# Interrupt vectors 0-255 are ordinals 100-355
# The 'interrupt' keyword takes care of the flags pushed on the stack by the interrupt
117 interrupt INT_Int11Handler() INT_Int11Handler
118 interrupt INT_Int12Handler() INT_Int12Handler
119 interrupt INT_Int13Handler() INT_Int13Handler
121 interrupt INT_Int15Handler() INT_Int15Handler
126 interrupt INT_Int1aHandler() INT_Int1aHandler
132 interrupt INT_Int20Handler() INT_Int20Handler
133 interrupt INT_Int21Handler() DOS3Call
# The '-interrupt' keyword takes care of the flags pushed on the stack by the interrupt
117 pascal -interrupt INT_Int11Handler() INT_Int11Handler
118 pascal -interrupt INT_Int12Handler() INT_Int12Handler
119 pascal -interrupt INT_Int13Handler() INT_Int13Handler
121 pascal -interrupt INT_Int15Handler() INT_Int15Handler
126 pascal -interrupt INT_Int1aHandler() INT_Int1aHandler
132 pascal -interrupt INT_Int20Handler() INT_Int20Handler
133 pascal -interrupt INT_Int21Handler() DOS3Call
# Note: int 25 and 26 don't pop the flags from the stack
137 register INT_Int25Handler() INT_Int25Handler
138 register INT_Int26Handler() INT_Int26Handler
142 interrupt INT_Int2aHandler() INT_Int2aHandler
147 interrupt INT_Int2fHandler() INT_Int2fHandler
149 interrupt INT_Int31Handler() INT_Int31Handler
161 interrupt INT_Int3dHandler() INT_Int3dHandler
165 interrupt INT_Int41Handler() INT_Int41Handler
175 interrupt INT_Int4bHandler() INT_Int4bHandler
192 interrupt INT_Int5cHandler() NetBIOSCall16
137 pascal -register INT_Int25Handler() INT_Int25Handler
138 pascal -register INT_Int26Handler() INT_Int26Handler
142 pascal -interrupt INT_Int2aHandler() INT_Int2aHandler
147 pascal -interrupt INT_Int2fHandler() INT_Int2fHandler
149 pascal -interrupt INT_Int31Handler() INT_Int31Handler
161 pascal -interrupt INT_Int3dHandler() INT_Int3dHandler
165 pascal -interrupt INT_Int41Handler() INT_Int41Handler
175 pascal -interrupt INT_Int4bHandler() INT_Int4bHandler
192 pascal -interrupt INT_Int5cHandler() NetBIOSCall16
# default handler for unimplemented interrupts
356 interrupt INT_DefaultHandler() INT_DefaultHandler
356 pascal -interrupt INT_DefaultHandler() INT_DefaultHandler
# VxDs. The first Vxd is at 400
#
#400+VXD_ID register <VxD handler>() <VxD handler>
#400+VXD_ID pascal -register <VxD handler>() <VxD handler>
#
401 register VXD_VMM() VXD_VMM
405 register VXD_Timer() VXD_Timer
409 register VXD_Reboot() VXD_Reboot
410 register VXD_VDD() VXD_VDD
412 register VXD_VMD() VXD_VMD
414 register VXD_Comm() VXD_Comm
#415 register VXD_Printer() VXD_Printer
423 register VXD_Shell() VXD_Shell
433 register VXD_PageFile() VXD_PageFile
438 register VXD_APM() VXD_APM
439 register VXD_VXDLoader() VXD_VXDLoader
445 register VXD_Win32s() VXD_Win32s
451 register VXD_ConfigMG() VXD_ConfigMG
455 register VXD_Enable() VXD_Enable
1490 register VXD_TimerAPI() VXD_TimerAPI
401 pascal -register VXD_VMM() VXD_VMM
405 pascal -register VXD_Timer() VXD_Timer
409 pascal -register VXD_Reboot() VXD_Reboot
410 pascal -register VXD_VDD() VXD_VDD
412 pascal -register VXD_VMD() VXD_VMD
414 pascal -register VXD_Comm() VXD_Comm
#415 pascal -register VXD_Printer() VXD_Printer
423 pascal -register VXD_Shell() VXD_Shell
433 pascal -register VXD_PageFile() VXD_PageFile
438 pascal -register VXD_APM() VXD_APM
439 pascal -register VXD_VXDLoader() VXD_VXDLoader
445 pascal -register VXD_Win32s() VXD_Win32s
451 pascal -register VXD_ConfigMG() VXD_ConfigMG
455 pascal -register VXD_Enable() VXD_Enable
1490 pascal -register VXD_TimerAPI() VXD_TimerAPI

View file

@ -878,11 +878,11 @@ debug_channels (atom cdrom console debug delayhlp dll dosfs dosmem file fixup
@ stub __eGetStatusWord
@ stdcall -ret64 _alldiv(long long long long) _alldiv
@ stdcall -ret64 _allmul(long long long long) _allmul
@ register -i386 _alloca_probe() NTDLL_alloca_probe
@ stdcall -register -i386 _alloca_probe() NTDLL_alloca_probe
@ stdcall -ret64 _allrem(long long long long) _allrem
@ stdcall -ret64 _aulldiv(long long long long) _aulldiv
@ stdcall -ret64 _aullrem(long long long long) _aullrem
@ register -i386 _chkstk() NTDLL_chkstk
@ stdcall -register -i386 _chkstk() NTDLL_chkstk
@ stub _fltused
@ cdecl _ftol() NTDLL__ftol
@ cdecl _itoa(long ptr long) _itoa

View file

@ -21,6 +21,16 @@
DEFAULT_DEBUG_CHANNEL(module);
typedef struct
{
void *module_start; /* 32-bit address of the module data */
int module_size; /* Size of the module data */
void *code_start; /* 32-bit address of DLL code */
void *data_start; /* 32-bit address of DLL data */
const char *owner; /* 32-bit dll that contains this dll */
const void *rsrc; /* resources data */
} BUILTIN16_DESCRIPTOR;
/* Table of all built-in DLLs */
#define MAX_DLLS 50
@ -167,63 +177,6 @@ HMODULE16 BUILTIN_LoadModule( LPCSTR name )
}
/***********************************************************************
* BUILTIN_GetEntryPoint16
*
* Return the ordinal, name, and type info corresponding to a CS:IP address.
* This is used only by relay debugging.
*/
LPCSTR BUILTIN_GetEntryPoint16( STACK16FRAME *frame, LPSTR name, WORD *pOrd )
{
WORD i, max_offset;
register BYTE *p;
NE_MODULE *pModule;
ET_BUNDLE *bundle;
ET_ENTRY *entry;
if (!(pModule = NE_GetPtr( FarGetOwner16( GlobalHandle16( frame->module_cs ) ))))
return NULL;
max_offset = 0;
*pOrd = 0;
bundle = (ET_BUNDLE *)((BYTE *)pModule + pModule->entry_table);
do
{
entry = (ET_ENTRY *)((BYTE *)bundle+6);
for (i = bundle->first + 1; i <= bundle->last; i++)
{
if ((entry->offs < frame->entry_ip)
&& (entry->segnum == 1) /* code segment ? */
&& (entry->offs >= max_offset))
{
max_offset = entry->offs;
*pOrd = i;
}
entry++;
}
} while ( (bundle->next)
&& (bundle = (ET_BUNDLE *)((BYTE *)pModule+bundle->next)));
/* Search for the name in the resident names table */
/* (built-in modules have no non-resident table) */
p = (BYTE *)pModule + pModule->name_table;
while (*p)
{
p += *p + 1 + sizeof(WORD);
if (*(WORD *)(p + *p + 1) == *pOrd) break;
}
sprintf( name, "%.*s.%d: %.*s",
*((BYTE *)pModule + pModule->name_table),
(char *)pModule + pModule->name_table + 1,
*pOrd, *p, (char *)(p + 1) );
/* Retrieve type info string */
return *(LPCSTR *)((LPBYTE)MapSL( MAKESEGPTR( frame->module_cs, frame->callfrom_ip )) + 4);
}
/***********************************************************************
* __wine_register_dll_16 (KERNEL32.@)
*

View file

@ -6,6 +6,8 @@
#include <assert.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include "wine/winbase16.h"
#include "winnt.h"
#include "module.h"
@ -116,14 +118,6 @@ void __wine_call_from_16_regs()
assert( FALSE );
}
/***********************************************************************
* __wine_call_from_16_thunk (KERNEL32.@)
*/
void __wine_call_from_16_thunk()
{
assert( FALSE );
}
DWORD WINAPI CALL32_CBClient( FARPROC proc, LPWORD args, DWORD *esi )
{ assert( FALSE ); }
@ -136,6 +130,65 @@ DWORD WINAPI CALL32_CBClientEx( FARPROC proc, LPWORD args, DWORD *esi, INT *nArg
extern char **debug_relay_excludelist,**debug_relay_includelist;
extern int RELAY_ShowDebugmsgRelay(const char *func);
/***********************************************************************
* get_entry_point
*
* Return the ordinal, name, and type info corresponding to a CS:IP address.
*/
static const CALLFROM16 *get_entry_point( STACK16FRAME *frame, LPSTR name, WORD *pOrd )
{
WORD i, max_offset;
register BYTE *p;
NE_MODULE *pModule;
ET_BUNDLE *bundle;
ET_ENTRY *entry;
if (!(pModule = NE_GetPtr( FarGetOwner16( GlobalHandle16( frame->module_cs ) ))))
return NULL;
max_offset = 0;
*pOrd = 0;
bundle = (ET_BUNDLE *)((BYTE *)pModule + pModule->entry_table);
do
{
entry = (ET_ENTRY *)((BYTE *)bundle+6);
for (i = bundle->first + 1; i <= bundle->last; i++)
{
if ((entry->offs < frame->entry_ip)
&& (entry->segnum == 1) /* code segment ? */
&& (entry->offs >= max_offset))
{
max_offset = entry->offs;
*pOrd = i;
}
entry++;
}
} while ( (bundle->next)
&& (bundle = (ET_BUNDLE *)((BYTE *)pModule+bundle->next)));
/* Search for the name in the resident names table */
/* (built-in modules have no non-resident table) */
p = (BYTE *)pModule + pModule->name_table;
while (*p)
{
p += *p + 1 + sizeof(WORD);
if (*(WORD *)(p + *p + 1) == *pOrd) break;
}
sprintf( name, "%.*s.%d: %.*s",
*((BYTE *)pModule + pModule->name_table),
(char *)pModule + pModule->name_table + 1,
*pOrd, *p, (char *)(p + 1) );
/* Retrieve entry point call structure */
p = MapSL( MAKESEGPTR( frame->module_cs, frame->callfrom_ip ) );
/* p now points to lret, get the start of CALLFROM16 structure */
return (CALLFROM16 *)(p - (BYTE *)&((CALLFROM16 *)0)->lret);
}
/***********************************************************************
* RELAY_DebugCallFrom16
*/
@ -144,111 +197,101 @@ void RELAY_DebugCallFrom16( CONTEXT86 *context )
STACK16FRAME *frame;
WORD ordinal;
char *args16, funstr[80];
const char *args;
int i, usecdecl, reg_func;
const CALLFROM16 *call;
int i;
if (!TRACE_ON(relay)) return;
frame = CURRENT_STACK16;
args = BUILTIN_GetEntryPoint16( frame, funstr, &ordinal );
if (!args) return; /* happens for the two snoop register relays */
call = get_entry_point( frame, funstr, &ordinal );
if (!call) return; /* happens for the two snoop register relays */
if (!RELAY_ShowDebugmsgRelay(funstr)) return;
DPRINTF( "%08lx:Call %s(",GetCurrentThreadId(),funstr);
VA_START16( args16 );
usecdecl = ( *args == 'c' );
args += 2;
reg_func = ( memcmp( args, "regs_", 5 ) == 0
|| memcmp( args, "intr_", 5 ) == 0 );
args += 5;
if (usecdecl)
if (call->lret == 0xcb66) /* cdecl */
{
while (*args)
for (i = 0; i < 20; i++)
{
switch(*args)
int type = (call->arg_types[i / 10] >> (3 * (i % 10))) & 7;
if (type == ARG_NONE) break;
if (i) DPRINTF( "," );
switch(type)
{
case 'w':
case 's':
DPRINTF( "0x%04x", *(WORD *)args16 );
args16 += 2;
case ARG_WORD:
case ARG_SWORD:
DPRINTF( "%04x", *(WORD *)args16 );
args16 += sizeof(WORD);
break;
case 'l':
DPRINTF( "0x%08x", *(int *)args16 );
args16 += 4;
case ARG_LONG:
DPRINTF( "%08x", *(int *)args16 );
args16 += sizeof(int);
break;
case 'p':
case ARG_PTR:
DPRINTF( "%04x:%04x", *(WORD *)(args16+2), *(WORD *)args16 );
args16 += 4;
args16 += sizeof(SEGPTR);
break;
case 't':
case 'T':
case ARG_STR:
DPRINTF( "%08x %s", *(int *)args16,
debugres_a( MapSL(*(SEGPTR *)args16 )));
args16 += sizeof(int);
break;
case ARG_SEGSTR:
DPRINTF( "%04x:%04x %s", *(WORD *)(args16+2), *(WORD *)args16,
debugres_a( MapSL(*(SEGPTR *)args16 )) );
args16 += 4;
args16 += sizeof(SEGPTR);
break;
default:
break;
}
args++;
if (*args) DPRINTF( "," );
}
}
else /* not cdecl */
{
/* Start with the last arg */
for (i = 0; args[i]; i++)
args16 += call->nArgs;
for (i = 0; i < 20; i++)
{
switch(args[i])
{
case 'w':
case 's':
args16 += 2;
break;
case 'l':
case 'p':
case 't':
case 'T':
args16 += 4;
break;
}
}
int type = (call->arg_types[i / 10] >> (3 * (i % 10))) & 7;
while (*args)
{
switch(*args)
if (type == ARG_NONE) break;
if (i) DPRINTF( "," );
switch(type)
{
case 'w':
case 's':
args16 -= 2;
DPRINTF( "0x%04x", *(WORD *)args16 );
case ARG_WORD:
case ARG_SWORD:
args16 -= sizeof(WORD);
DPRINTF( "%04x", *(WORD *)args16 );
break;
case 'l':
args16 -= 4;
DPRINTF( "0x%08x", *(int *)args16 );
case ARG_LONG:
args16 -= sizeof(int);
DPRINTF( "%08x", *(int *)args16 );
break;
case 't':
args16 -= 4;
DPRINTF( "0x%08x %s", *(int *)args16,
debugres_a( MapSL(*(SEGPTR *)args16 )));
break;
case 'p':
args16 -= 4;
case ARG_PTR:
args16 -= sizeof(SEGPTR);
DPRINTF( "%04x:%04x", *(WORD *)(args16+2), *(WORD *)args16 );
break;
case 'T':
args16 -= 4;
DPRINTF( "%04x:%04x %s", *(WORD *)(args16+2), *(WORD *)args16,
case ARG_STR:
args16 -= sizeof(int);
DPRINTF( "%08x %s", *(int *)args16,
debugres_a( MapSL(*(SEGPTR *)args16 )));
break;
case ARG_SEGSTR:
args16 -= sizeof(SEGPTR);
DPRINTF( "%04x:%04x %s", *(WORD *)(args16+2), *(WORD *)args16,
debugres_a( MapSL(*(SEGPTR *)args16 )) );
break;
default:
break;
}
args++;
if (*args) DPRINTF( "," );
}
}
DPRINTF( ") ret=%04x:%04x ds=%04x\n", frame->cs, frame->ip, frame->ds );
VA_END16( args16 );
if (reg_func)
if (call->arg_types[0] & ARG_REGISTER)
DPRINTF(" AX=%04x BX=%04x CX=%04x DX=%04x SI=%04x DI=%04x ES=%04x EFL=%08lx\n",
AX_reg(context), BX_reg(context), CX_reg(context),
DX_reg(context), SI_reg(context), DI_reg(context),
@ -266,27 +309,16 @@ void RELAY_DebugCallFrom16Ret( CONTEXT86 *context, int ret_val )
STACK16FRAME *frame;
WORD ordinal;
char funstr[80];
const char *args;
const CALLFROM16 *call;
if (!TRACE_ON(relay)) return;
frame = CURRENT_STACK16;
args = BUILTIN_GetEntryPoint16( frame, funstr, &ordinal );
if (!args) return;
call = get_entry_point( frame, funstr, &ordinal );
if (!call) return;
if (!RELAY_ShowDebugmsgRelay(funstr)) return;
DPRINTF( "%08lx:Ret %s() ",GetCurrentThreadId(),funstr);
if ( memcmp( args+2, "long_", 5 ) == 0 )
{
DPRINTF( "retval=0x%08x ret=%04x:%04x ds=%04x\n",
ret_val, frame->cs, frame->ip, frame->ds );
}
else if ( memcmp( args+2, "word_", 5 ) == 0 )
{
DPRINTF( "retval=0x%04x ret=%04x:%04x ds=%04x\n",
ret_val & 0xffff, frame->cs, frame->ip, frame->ds );
}
else if ( memcmp( args+2, "regs_", 5 ) == 0
|| memcmp( args+2, "intr_", 5 ) == 0 )
if (call->arg_types[0] & ARG_REGISTER)
{
DPRINTF("retval=none ret=%04x:%04x ds=%04x\n",
(WORD)context->SegCs, LOWORD(context->Eip), (WORD)context->SegDs);
@ -295,7 +327,16 @@ void RELAY_DebugCallFrom16Ret( CONTEXT86 *context, int ret_val )
DX_reg(context), SI_reg(context), DI_reg(context),
(WORD)context->SegEs, context->EFlags );
}
else if (call->arg_types[0] & ARG_RET16)
{
DPRINTF( "retval=%04x ret=%04x:%04x ds=%04x\n",
ret_val & 0xffff, frame->cs, frame->ip, frame->ds );
}
else
{
DPRINTF( "retval=%08x ret=%04x:%04x ds=%04x\n",
ret_val, frame->cs, frame->ip, frame->ds );
}
SYSLEVEL_CheckNotLevel( 2 );
}
@ -326,10 +367,10 @@ void RELAY_DebugCallTo16( LPVOID target, int nb_args, BOOL reg_func )
DPRINTF("%08lx:CallTo16(func=%04lx:%04x,ds=%04lx",
GetCurrentThreadId(),
context->SegCs, LOWORD(context->Eip), context->SegDs );
while (nb_args--) DPRINTF( ",0x%04x", *--stack16 );
DPRINTF(") ss:sp=%04x:%04x\n", SELECTOROF(teb->cur_stack),
while (nb_args--) DPRINTF( ",%04x", *--stack16 );
DPRINTF(") ss:sp=%04x:%04x", SELECTOROF(teb->cur_stack),
OFFSETOF(teb->cur_stack) );
DPRINTF(" AX=%04x BX=%04x CX=%04x DX=%04x SI=%04x DI=%04x BP=%04x ES=%04x FS=%04x\n",
DPRINTF(" ax=%04x bx=%04x cx=%04x dx=%04x si=%04x di=%04x bp=%04x es=%04x fs=%04x\n",
AX_reg(context), BX_reg(context), CX_reg(context),
DX_reg(context), SI_reg(context), DI_reg(context),
BP_reg(context), (WORD)context->SegEs, (WORD)context->SegFs );
@ -339,7 +380,7 @@ void RELAY_DebugCallTo16( LPVOID target, int nb_args, BOOL reg_func )
DPRINTF("%08lx:CallTo16(func=%04x:%04x,ds=%04x",
GetCurrentThreadId(),
HIWORD(target), LOWORD(target), SELECTOROF(teb->cur_stack) );
while (nb_args--) DPRINTF( ",0x%04x", *--stack16 );
while (nb_args--) DPRINTF( ",%04x", *--stack16 );
DPRINTF(") ss:sp=%04x:%04x\n", SELECTOROF(teb->cur_stack),
OFFSETOF(teb->cur_stack) );
}
@ -357,7 +398,7 @@ void RELAY_DebugCallTo16Ret( BOOL reg_func, int ret_val )
if (!reg_func)
{
DPRINTF("%08lx:RetFrom16() ss:sp=%04x:%04x retval=0x%08x\n",
DPRINTF("%08lx:RetFrom16() ss:sp=%04x:%04x retval=%08x\n",
GetCurrentThreadId(),
SELECTOROF(NtCurrentTeb()->cur_stack),
OFFSETOF(NtCurrentTeb()->cur_stack), ret_val);
@ -366,11 +407,11 @@ void RELAY_DebugCallTo16Ret( BOOL reg_func, int ret_val )
{
CONTEXT86 *context = (CONTEXT86 *)ret_val;
DPRINTF("%08lx:RetFrom16() ss:sp=%04x:%04x\n",
DPRINTF("%08lx:RetFrom16() ss:sp=%04x:%04x ",
GetCurrentThreadId(),
SELECTOROF(NtCurrentTeb()->cur_stack),
OFFSETOF(NtCurrentTeb()->cur_stack));
DPRINTF(" AX=%04x BX=%04x CX=%04x DX=%04x BP=%04x SP=%04x\n",
DPRINTF(" ax=%04x bx=%04x cx=%04x dx=%04x bp=%04x sp=%04x\n",
AX_reg(context), BX_reg(context), CX_reg(context),
DX_reg(context), BP_reg(context), LOWORD(context->Esp));
}

View file

@ -13,9 +13,10 @@
struct _CONTEXT86;
struct _STACK16FRAME;
#ifdef __i386__
#include "pshpack1.h"
#ifdef __i386__
typedef struct
{
WORD pushw_bp; /* pushw %bp */
@ -32,45 +33,51 @@ typedef struct
BYTE lcall; /* lcall __FLATCS__:glue */
void *glue;
WORD flatcs;
BYTE prefix; /* lret $nArgs */
BYTE lret;
WORD lret; /* lret $nArgs */
WORD nArgs;
LPCSTR profile; /* profile string */
DWORD arg_types[2]; /* type of each argument */
} CALLFROM16;
#include "poppack.h"
#else
typedef struct
{
void (*target)();
int callfrom16;
WORD call; /* call CALLFROM16 */
short callfrom16;
} ENTRYPOINT16;
typedef struct
{
LPCSTR profile;
WORD lret; /* lret $nArgs */
WORD nArgs;
DWORD arg_types[2]; /* type of each argument */
} CALLFROM16;
#endif
typedef struct
#include "poppack.h"
/* argument type flags for relay debugging */
enum arg_types
{
void *module_start; /* 32-bit address of the module data */
int module_size; /* Size of the module data */
void *code_start; /* 32-bit address of DLL code */
void *data_start; /* 32-bit address of DLL data */
const char *owner; /* 32-bit dll that contains this dll */
const void *rsrc; /* resources data */
} BUILTIN16_DESCRIPTOR;
ARG_NONE = 0, /* indicates end of arg list */
ARG_WORD, /* unsigned word */
ARG_SWORD, /* signed word */
ARG_LONG, /* long or segmented pointer */
ARG_PTR, /* linear pointer */
ARG_STR, /* linear pointer to null-terminated string */
ARG_SEGSTR /* segmented pointer to null-terminated string */
};
/* flags added to arg_types[0] */
#define ARG_RET16 0x80000000 /* function returns 16-bit value */
#define ARG_REGISTER 0x40000000 /* function is register */
extern HMODULE16 BUILTIN_LoadModule( LPCSTR name );
extern LPCSTR BUILTIN_GetEntryPoint16( struct _STACK16FRAME *frame, LPSTR name, WORD *pOrd );
extern void __wine_register_dll_16( const BUILTIN16_DESCRIPTOR *descr );
extern WORD __wine_call_from_16_word();
extern LONG __wine_call_from_16_long();
extern void __wine_call_from_16_regs();
extern void __wine_call_from_16_thunk();
#endif /* __WINE_BUILTIN16_H */

View file

@ -157,8 +157,108 @@ static inline void RELAY_PrintArgs( int *args, int nb_args, unsigned int typemas
}
typedef LONGLONG (*LONGLONG_CPROC)();
typedef LONGLONG WINAPI (*LONGLONG_FARPROC)();
/***********************************************************************
* call_cdecl_function
*/
static LONGLONG call_cdecl_function( LONGLONG_CPROC func, int nb_args, const int *args )
{
LONGLONG ret;
switch(nb_args)
{
case 0: ret = func(); break;
case 1: ret = func(args[0]); break;
case 2: ret = func(args[0],args[1]); break;
case 3: ret = func(args[0],args[1],args[2]); break;
case 4: ret = func(args[0],args[1],args[2],args[3]); break;
case 5: ret = func(args[0],args[1],args[2],args[3],args[4]); break;
case 6: ret = func(args[0],args[1],args[2],args[3],args[4],
args[5]); break;
case 7: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6]); break;
case 8: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7]); break;
case 9: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8]); break;
case 10: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9]); break;
case 11: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10]); break;
case 12: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],
args[11]); break;
case 13: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12]); break;
case 14: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12],args[13]); break;
case 15: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12],args[13],args[14]); break;
case 16: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12],args[13],args[14],args[15]); break;
default:
ERR( "Unsupported nb of args %d\n", nb_args );
assert(FALSE);
}
return ret;
}
/***********************************************************************
* call_stdcall_function
*/
static LONGLONG call_stdcall_function( LONGLONG_FARPROC func, int nb_args, const int *args )
{
LONGLONG ret;
switch(nb_args)
{
case 0: ret = func(); break;
case 1: ret = func(args[0]); break;
case 2: ret = func(args[0],args[1]); break;
case 3: ret = func(args[0],args[1],args[2]); break;
case 4: ret = func(args[0],args[1],args[2],args[3]); break;
case 5: ret = func(args[0],args[1],args[2],args[3],args[4]); break;
case 6: ret = func(args[0],args[1],args[2],args[3],args[4],
args[5]); break;
case 7: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6]); break;
case 8: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7]); break;
case 9: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8]); break;
case 10: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9]); break;
case 11: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10]); break;
case 12: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],
args[11]); break;
case 13: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12]); break;
case 14: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12],args[13]); break;
case 15: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12],args[13],args[14]); break;
case 16: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12],args[13],args[14],args[15]); break;
default:
ERR( "Unsupported nb of args %d\n", nb_args );
assert(FALSE);
}
return ret;
}
/***********************************************************************
* RELAY_CallFrom32
*
@ -190,90 +290,13 @@ static LONGLONG RELAY_CallFrom32( int ret_addr, ... )
if (relay->ret == 0xc3) /* cdecl */
{
LONGLONG (*cfunc)() = relay->orig;
switch(nb_args)
{
case 0: ret = cfunc(); break;
case 1: ret = cfunc(args[0]); break;
case 2: ret = cfunc(args[0],args[1]); break;
case 3: ret = cfunc(args[0],args[1],args[2]); break;
case 4: ret = cfunc(args[0],args[1],args[2],args[3]); break;
case 5: ret = cfunc(args[0],args[1],args[2],args[3],args[4]); break;
case 6: ret = cfunc(args[0],args[1],args[2],args[3],args[4],
args[5]); break;
case 7: ret = cfunc(args[0],args[1],args[2],args[3],args[4],args[5],
args[6]); break;
case 8: ret = cfunc(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7]); break;
case 9: ret = cfunc(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8]); break;
case 10: ret = cfunc(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9]); break;
case 11: ret = cfunc(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10]); break;
case 12: ret = cfunc(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],
args[11]); break;
case 13: ret = cfunc(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12]); break;
case 14: ret = cfunc(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12],args[13]); break;
case 15: ret = cfunc(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12],args[13],args[14]); break;
case 16: ret = cfunc(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12],args[13],args[14],args[15]); break;
default:
ERR( "Unsupported nb of args %d\n", nb_args );
assert(FALSE);
}
ret = call_cdecl_function( (LONGLONG_CPROC)relay->orig, nb_args, args );
}
else /* stdcall */
{
LONGLONG_FARPROC func = relay->orig;
switch(nb_args)
{
case 0: ret = func(); break;
case 1: ret = func(args[0]); break;
case 2: ret = func(args[0],args[1]); break;
case 3: ret = func(args[0],args[1],args[2]); break;
case 4: ret = func(args[0],args[1],args[2],args[3]); break;
case 5: ret = func(args[0],args[1],args[2],args[3],args[4]); break;
case 6: ret = func(args[0],args[1],args[2],args[3],args[4],
args[5]); break;
case 7: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6]); break;
case 8: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7]); break;
case 9: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8]); break;
case 10: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9]); break;
case 11: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10]); break;
case 12: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],
args[11]); break;
case 13: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12]); break;
case 14: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12],args[13]); break;
case 15: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12],args[13],args[14]); break;
case 16: ret = func(args[0],args[1],args[2],args[3],args[4],args[5],
args[6],args[7],args[8],args[9],args[10],args[11],
args[12],args[13],args[14],args[15]); break;
default:
ERR( "Unsupported nb of args %d\n", nb_args );
assert(FALSE);
}
ret = call_stdcall_function( (LONGLONG_FARPROC)relay->orig, nb_args, args );
}
if (ret64)
DPRINTF( "%08lx:Ret %s() retval=%08x%08x ret=%08x\n",
GetCurrentThreadId(),
@ -303,7 +326,7 @@ void WINAPI RELAY_DoCallFrom32Regs( CONTEXT86 *context )
{
char buffer[80];
int* args;
FARPROC func;
int args_copy[17];
BYTE *entry_point;
BYTE *relay_addr = *((BYTE **)context->Esp - 1);
@ -319,7 +342,6 @@ void WINAPI RELAY_DoCallFrom32Regs( CONTEXT86 *context )
entry_point = (BYTE *)relay->orig;
assert( *entry_point == 0xe8 /* lcall */ );
func = *(FARPROC *)(entry_point + 5);
get_entry_point( buffer, relay );
@ -335,36 +357,16 @@ void WINAPI RELAY_DoCallFrom32Regs( CONTEXT86 *context )
context->SegEs, context->SegGs, context->EFlags );
/* Now call the real function */
switch(nb_args)
memcpy( args_copy, args, nb_args * sizeof(args[0]) );
args_copy[nb_args] = (int)context; /* append context argument */
if (relay->ret == 0xc3) /* cdecl */
{
case 0: func(context); break;
case 1: func(args[0],context); break;
case 2: func(args[0],args[1],context); break;
case 3: func(args[0],args[1],args[2],context); break;
case 4: func(args[0],args[1],args[2],args[3],context); break;
case 5: func(args[0],args[1],args[2],args[3],args[4],context); break;
case 6: func(args[0],args[1],args[2],args[3],args[4],args[5],context); break;
case 7: func(args[0],args[1],args[2],args[3],args[4],args[5],args[6],context); break;
case 8: func(args[0],args[1],args[2],args[3],args[4],args[5],args[6],args[7],context); break;
case 9: func(args[0],args[1],args[2],args[3],args[4],args[5],args[6],args[7],args[8],
context); break;
case 10: func(args[0],args[1],args[2],args[3],args[4],args[5],args[6],args[7],args[8],
args[9],context); break;
case 11: func(args[0],args[1],args[2],args[3],args[4],args[5],args[6],args[7],args[8],
args[9],args[10],context); break;
case 12: func(args[0],args[1],args[2],args[3],args[4],args[5],args[6],args[7],args[8],
args[9],args[10],args[11],context); break;
case 13: func(args[0],args[1],args[2],args[3],args[4],args[5],args[6],args[7],args[8],
args[9],args[10],args[11],args[12],context); break;
case 14: func(args[0],args[1],args[2],args[3],args[4],args[5],args[6],args[7],args[8],
args[9],args[10],args[11],args[12],args[13],context); break;
case 15: func(args[0],args[1],args[2],args[3],args[4],args[5],args[6],args[7],args[8],
args[9],args[10],args[11],args[12],args[13],args[14],context); break;
case 16: func(args[0],args[1],args[2],args[3],args[4],args[5], args[6],args[7],args[8],
args[9],args[10],args[11],args[12],args[13],args[14],args[15],context); break;
default:
ERR( "Unsupported nb of args %d\n", nb_args );
assert(FALSE);
call_cdecl_function( *(LONGLONG_CPROC *)(entry_point + 5), nb_args+1, args_copy );
}
else /* stdcall */
{
call_stdcall_function( *(LONGLONG_FARPROC *)(entry_point + 5), nb_args+1, args_copy );
}
DPRINTF( "%08lx:Ret %s() retval=%08lx ret=%08lx fs=%04lx\n",

View file

@ -73,12 +73,14 @@ point, or "@" for automatic ordinal allocation (Win32 only).
"FLAGS" is a series of optional flags, preceded by a '-' character.
The supported flags are:
"-noimport": the entry point is not made available for importing
from winelib applications (Win32 only).
"-norelay": the entry point is not displayed in relay debugging
traces (Win32 only).
"-ret64": the function returns a 64-bit value (Win32 only).
"-i386": the entry point is only available on i386 platforms.
"-noimport": the entry point is not made available for importing
from winelib applications (Win32 only).
"-norelay": the entry point is not displayed in relay debugging
traces (Win32 only).
"-ret64": the function returns a 64-bit value (Win32 only).
"-i386": the entry point is only available on i386 platforms.
"-register": the function uses CPU register to pass arguments.
"-interrupt": the function is an interrupt handler routine.
Lines whose first character is a '#' will be ignored as comments.
@ -105,8 +107,6 @@ instead of "EXPORTNAME" for ordinal-only exports.
"FUNCTYPE" should be one of:
- "pascal16" for a Win16 function returning a 16-bit value
- "pascal" for a Win16 function returning a 32-bit value
- "register" for a function using CPU register to pass arguments
- "interrupt" for a Win16 interrupt handler routine
- "stdcall" for a normal Win32 function
- "cdecl" for a Win32 function using the C calling convention
- "varargs" for a Win32 function taking a variable number of arguments

View file

@ -40,8 +40,6 @@ typedef enum
TYPE_PASCAL_16, /* pascal function with 16-bit return (Win16) */
TYPE_PASCAL, /* pascal function with 32-bit return (Win16) */
TYPE_ABS, /* absolute value (Win16) */
TYPE_REGISTER, /* register function */
TYPE_INTERRUPT, /* interrupt handler function (Win16) */
TYPE_STUB, /* unimplemented stub */
TYPE_STDCALL, /* stdcall function (Win32) */
TYPE_CDECL, /* cdecl function (Win32) */
@ -106,6 +104,8 @@ typedef struct
#define FLAG_NORELAY 0x02 /* don't use relay debugging for this function */
#define FLAG_RET64 0x04 /* function returns a 64-bit value */
#define FLAG_I386 0x08 /* function is i386 only */
#define FLAG_REGISTER 0x10 /* use register calling convention */
#define FLAG_INTERRUPT 0x20 /* function is an interrupt handler */
/* Offset of a structure field relative to the start of the struct */
#define STRUCTOFFSET(type,field) ((int)&((type *)0)->field)

View file

@ -250,8 +250,11 @@ static void add_extra_undef_symbols(void)
for (i = 0; i < nb_entry_points; i++)
{
ORDDEF *odp = EntryPoints[i];
if (odp->type != TYPE_REGISTER) continue;
ADD_SYM( "__wine_call_from_32_regs" );
if (odp->flags & FLAG_REGISTER)
{
ADD_SYM( "__wine_call_from_32_regs" );
break;
}
}
if (count)

View file

@ -35,8 +35,6 @@ static const char * const TypeNames[TYPE_NBTYPES] =
"pascal16", /* TYPE_PASCAL_16 */
"pascal", /* TYPE_PASCAL */
"equate", /* TYPE_ABS */
"register", /* TYPE_REGISTER */
"interrupt", /* TYPE_INTERRUPT */
"stub", /* TYPE_STUB */
"stdcall", /* TYPE_STDCALL */
"cdecl", /* TYPE_CDECL */
@ -51,6 +49,8 @@ static const char * const FlagNames[] =
"norelay", /* FLAG_NORELAY */
"ret64", /* FLAG_RET64 */
"i386", /* FLAG_I386 */
"register", /* FLAG_REGISTER */
"interrupt", /* FLAG_INTERRUPT */
NULL
};
@ -214,6 +214,8 @@ static void ParseExportFunction( ORDDEF *odp )
case SPEC_WIN32:
if ((odp->type == TYPE_PASCAL) || (odp->type == TYPE_PASCAL_16))
fatal_error( "'pascal' not supported for Win32\n" );
if (odp->flags & FLAG_INTERRUPT)
fatal_error( "'interrupt' not supported for Win32\n" );
break;
default:
break;
@ -302,29 +304,6 @@ static void ParseStub( ORDDEF *odp )
}
/*******************************************************************
* ParseInterrupt
*
* Parse an 'interrupt' definition.
*/
static void ParseInterrupt( ORDDEF *odp )
{
const char *token;
if (SpecType == SPEC_WIN32)
fatal_error( "'interrupt' not supported for Win32\n" );
token = GetToken(0);
if (*token != '(') fatal_error( "Expected '(' got '%s'\n", token );
token = GetToken(0);
if (*token != ')') fatal_error( "Expected ')' got '%s'\n", token );
odp->u.func.arg_types[0] = '\0';
odp->link_name = xstrdup( GetToken(0) );
}
/*******************************************************************
* ParseExtern
*
@ -423,7 +402,6 @@ static void ParseOrdinal(int ordinal)
case TYPE_VARIABLE:
ParseVariable( odp );
break;
case TYPE_REGISTER:
case TYPE_PASCAL_16:
case TYPE_PASCAL:
case TYPE_STDCALL:
@ -431,9 +409,6 @@ static void ParseOrdinal(int ordinal)
case TYPE_CDECL:
ParseExportFunction( odp );
break;
case TYPE_INTERRUPT:
ParseInterrupt( odp );
break;
case TYPE_ABS:
ParseEquate( odp );
break;

View file

@ -27,6 +27,28 @@ __ASM_GLOBAL_FUNC( __get_cs, "movw %cs,%ax\n\tret" );
#endif /* __i386__ */
/*******************************************************************
* output_file_header
*
* Output a file header with the common declarations we need.
*/
static void output_file_header( FILE *outfile )
{
fprintf( outfile, "/* File generated automatically from %s; do not edit! */\n\n",
input_file_name );
fprintf( outfile, "extern struct\n{\n" );
fprintf( outfile, " void *base[8192];\n" );
fprintf( outfile, " unsigned long limit[8192];\n" );
fprintf( outfile, " unsigned char flags[8192];\n" );
fprintf( outfile, "} wine_ldt_copy;\n\n" );
#ifdef __i386__
fprintf( outfile, "#define __stdcall __attribute__((__stdcall__))\n\n" );
#else
fprintf( outfile, "#define __stdcall\n\n" );
#endif
}
/*******************************************************************
* StoreVariableCode
*
@ -200,8 +222,6 @@ static int BuildModule16( FILE *outfile, int max_code_offset,
case TYPE_CDECL:
case TYPE_PASCAL:
case TYPE_PASCAL_16:
case TYPE_REGISTER:
case TYPE_INTERRUPT:
case TYPE_STUB:
selector = 1; /* Code selector */
break;
@ -323,7 +343,6 @@ static void BuildCallFrom16Func( FILE *outfile, char *profile, char *prefix, int
case 's': /* s_word */
argsize += 2;
break;
case 'l': /* long or segmented pointer */
case 'T': /* segmented pointer to null-terminated string */
case 'p': /* linear pointer */
@ -332,34 +351,32 @@ static void BuildCallFrom16Func( FILE *outfile, char *profile, char *prefix, int
break;
}
ret_type = reg_func? "void" : short_ret? "WORD" : "LONG";
ret_type = reg_func? "void" : short_ret ? "unsigned short" : "unsigned int";
fprintf( outfile, "typedef %s WINAPI (*proc_%s_t)( ",
ret_type, profile );
fprintf( outfile, "typedef %s __stdcall (*proc_%s_t)( ", ret_type, profile );
args = profile + 7;
for ( i = 0; args[i]; i++ )
{
if ( i ) fprintf( outfile, ", " );
switch (args[i])
{
case 'w': fprintf( outfile, "WORD" ); break;
case 's': fprintf( outfile, "INT16" ); break;
case 'l': case 'T': fprintf( outfile, "LONG" ); break;
case 'p': case 't': fprintf( outfile, "LPVOID" ); break;
case 'w': fprintf( outfile, "unsigned short" ); break;
case 's': fprintf( outfile, "short" ); break;
case 'l': case 'T': fprintf( outfile, "unsigned int" ); break;
case 'p': case 't': fprintf( outfile, "void *" ); break;
}
}
if ( reg_func )
fprintf( outfile, "%sstruct _CONTEXT86 *", i? ", " : "" );
fprintf( outfile, "%svoid *", i? ", " : "" );
else if ( !i )
fprintf( outfile, "void" );
fprintf( outfile, " );\n" );
fprintf( outfile, "%s%s WINAPI %s_CallFrom16_%s( FARPROC proc, LPBYTE args%s )\n{\n",
local? "static " : "", ret_type, prefix, profile,
reg_func? ", struct _CONTEXT86 *context" : "" );
fprintf( outfile, " %s((proc_%s_t) proc) (\n",
reg_func? "" : "return ", profile );
fprintf( outfile, "%s%s __stdcall %s_CallFrom16_%s( proc_%s_t proc, unsigned char *args%s )\n",
local? "static " : "", ret_type, prefix, profile, profile,
reg_func? ", void *context" : "" );
fprintf( outfile, "{\n %sproc(\n", reg_func ? "" : "return " );
args = profile + 7;
pos = !usecdecl? argsize : 0;
for ( i = 0; args[i]; i++ )
@ -370,27 +387,27 @@ static void BuildCallFrom16Func( FILE *outfile, char *profile, char *prefix, int
{
case 'w': /* word */
if ( !usecdecl ) pos -= 2;
fprintf( outfile, "*(WORD *)(args+%d)", pos );
fprintf( outfile, "*(unsigned short *)(args+%d)", pos );
if ( usecdecl ) pos += 2;
break;
case 's': /* s_word */
if ( !usecdecl ) pos -= 2;
fprintf( outfile, "*(INT16 *)(args+%d)", pos );
fprintf( outfile, "*(short *)(args+%d)", pos );
if ( usecdecl ) pos += 2;
break;
case 'l': /* long or segmented pointer */
case 'T': /* segmented pointer to null-terminated string */
if ( !usecdecl ) pos -= 4;
fprintf( outfile, "*(LONG *)(args+%d)", pos );
fprintf( outfile, "*(unsigned int *)(args+%d)", pos );
if ( usecdecl ) pos += 4;
break;
case 'p': /* linear pointer */
case 't': /* linear pointer to null-terminated string */
if ( !usecdecl ) pos -= 4;
fprintf( outfile, "((char*)wine_ldt_copy.base[*(WORD*)(args+%d) >> 3] + *(WORD*)(args+%d))",
fprintf( outfile, "((char*)wine_ldt_copy.base[*(unsigned short*)(args+%d) >> 3] + *(unsigned short*)(args+%d))",
pos + 2, pos );
if ( usecdecl ) pos += 4;
break;
@ -435,31 +452,44 @@ static void BuildCallTo16Func( FILE *outfile, char *profile, char *prefix )
exit(1);
}
fprintf( outfile, "%s CALLBACK %s_CallTo16_%s( FARPROC16 proc",
short_ret? "WORD" : "LONG", prefix, profile );
fprintf( outfile, "unsigned %s __stdcall %s_CallTo16_%s( void (*proc)()",
short_ret? "short" : "int", prefix, profile );
args = profile + 5;
for ( i = 0; args[i]; i++ )
{
fprintf( outfile, ", " );
switch (args[i])
{
case 'w': fprintf( outfile, "WORD" ); argsize += 2; break;
case 'l': fprintf( outfile, "LONG" ); argsize += 4; break;
case 'w': fprintf( outfile, "unsigned short" ); argsize += 2; break;
case 'l': fprintf( outfile, "unsigned int" ); argsize += 4; break;
}
fprintf( outfile, " arg%d", i+1 );
}
fprintf( outfile, " )\n{\n" );
#ifdef __i386__
if ( argsize > 0 )
fprintf( outfile, " LPBYTE args = (LPBYTE)CURRENT_STACK16;\n" );
{
fprintf( outfile, " char *args;\n" );
fprintf( outfile, " unsigned int cur_stack;\n\n" );
fprintf( outfile, "#ifdef __GNUC__\n" );
fprintf( outfile, " __asm__(\".byte 0x64\\n\\tmovl (0x%x),%%0\" : \"=r\" (cur_stack));\n",
STACKOFFSET );
fprintf( outfile, "#else\n" );
fprintf( outfile, " extern char *NtCurrentTeb(void);\n" );
fprintf( outfile, " cur_stack = *(unsigned int *)(NtCurrentTeb() + 0x%x);\n",
STACKOFFSET );
fprintf( outfile, "#endif\n" );
fprintf( outfile, " args = (char *)wine_ldt_copy.base[cur_stack >> 19] + (cur_stack & 0xffff);\n" );
}
args = profile + 5;
for ( i = 0; args[i]; i++ )
{
switch (args[i])
{
case 'w': fprintf( outfile, " args -= sizeof(WORD); *(WORD" ); break;
case 'l': fprintf( outfile, " args -= sizeof(LONG); *(LONG" ); break;
case 'w': fprintf( outfile, " args -= sizeof(unsigned short); *(unsigned short" ); break;
case 'l': fprintf( outfile, " args -= sizeof(unsigned int); *(unsigned int" ); break;
default: fprintf( stderr, "Unexpected case '%c' in BuildCallTo16Func\n",
args[i] );
}
@ -468,6 +498,26 @@ static void BuildCallTo16Func( FILE *outfile, char *profile, char *prefix )
fprintf( outfile, " return wine_call_to_16_%s( proc, %d );\n}\n\n",
short_ret? "word" : "long", argsize );
#else /* __i386__ */
fprintf( outfile, " assert(0);\n}\n\n" );
#endif /* __i386__ */
}
/*******************************************************************
* get_function_name
*/
static const char *get_function_name( const ORDDEF *odp )
{
static char buffer[80];
sprintf( buffer, "%s_%s_%s",
(odp->type == TYPE_CDECL) ? "c" : "p",
(odp->flags & FLAG_REGISTER) ? "regs" :
(odp->flags & FLAG_INTERRUPT) ? "intr" :
(odp->type == TYPE_PASCAL_16) ? "word" : "long",
odp->u.func.arg_types );
return buffer;
}
@ -478,18 +528,20 @@ static int Spec16TypeCompare( const void *e1, const void *e2 )
{
const ORDDEF *odp1 = *(const ORDDEF **)e1;
const ORDDEF *odp2 = *(const ORDDEF **)e2;
int retval;
int type1 = (odp1->type == TYPE_CDECL) ? 0
: (odp1->type == TYPE_REGISTER) ? 3
: (odp1->type == TYPE_INTERRUPT) ? 4
: (odp1->type == TYPE_PASCAL_16) ? 1 : 2;
int type2 = (odp2->type == TYPE_CDECL) ? 0
: (odp2->type == TYPE_REGISTER) ? 3
: (odp2->type == TYPE_INTERRUPT) ? 4
: (odp2->type == TYPE_PASCAL_16) ? 1 : 2;
int retval = type1 - type2;
if (odp1->flags & FLAG_REGISTER) type1 += 4;
if (odp1->flags & FLAG_INTERRUPT) type1 += 8;
if (odp2->flags & FLAG_REGISTER) type2 += 4;
if (odp2->flags & FLAG_INTERRUPT) type2 += 8;
retval = type1 - type2;
if ( !retval )
retval = strcmp( odp1->u.func.arg_types, odp2->u.func.arg_types );
@ -567,15 +619,11 @@ void BuildSpec16File( FILE *outfile )
/* File header */
fprintf( outfile, "/* File generated automatically from %s; do not edit! */\n\n",
input_file_name );
fprintf( outfile, "#include \"builtin16.h\"\n\n" );
fprintf( outfile, "extern struct\n{\n" );
fprintf( outfile, " void *base[8192];\n" );
fprintf( outfile, " unsigned long limit[8192];\n" );
fprintf( outfile, " unsigned char flags[8192];\n" );
fprintf( outfile, "} wine_ldt_copy;\n\n" );
output_file_header( outfile );
fprintf( outfile, "extern unsigned short __wine_call_from_16_word();\n" );
fprintf( outfile, "extern unsigned int __wine_call_from_16_long();\n" );
fprintf( outfile, "extern void __wine_call_from_16_regs();\n" );
fprintf( outfile, "extern void __wine_call_from_16_thunk();\n" );
data = (unsigned char *)xmalloc( 0x10000 );
memset( data, 0, 16 );
@ -584,12 +632,6 @@ void BuildSpec16File( FILE *outfile )
fprintf( outfile, "static const char dllname[] = \"%s\";\n\n", DLLName );
#ifdef __i386__
fprintf( outfile, "#define __stdcall __attribute__((__stdcall__))\n\n" );
#else
fprintf( outfile, "#define __stdcall\n\n" );
#endif
output_stub_funcs( outfile );
/* Build sorted list of all argument types, without duplicates */
@ -602,8 +644,6 @@ void BuildSpec16File( FILE *outfile )
if (!odp) continue;
switch (odp->type)
{
case TYPE_REGISTER:
case TYPE_INTERRUPT:
case TYPE_CDECL:
case TYPE_PASCAL:
case TYPE_PASCAL_16:
@ -631,13 +671,7 @@ void BuildSpec16File( FILE *outfile )
{
char profile[101];
sprintf( profile, "%s_%s_%s",
(typelist[i]->type == TYPE_CDECL) ? "c" : "p",
(typelist[i]->type == TYPE_REGISTER) ? "regs" :
(typelist[i]->type == TYPE_INTERRUPT) ? "intr" :
(typelist[i]->type == TYPE_PASCAL_16) ? "word" : "long",
typelist[i]->u.func.arg_types );
strcpy( profile, get_function_name( typelist[i] ));
BuildCallFrom16Func( outfile, profile, DLLName, TRUE );
}
#endif
@ -650,8 +684,6 @@ void BuildSpec16File( FILE *outfile )
if (!odp) continue;
switch(odp->type)
{
case TYPE_REGISTER:
case TYPE_INTERRUPT:
case TYPE_CDECL:
case TYPE_PASCAL:
case TYPE_PASCAL_16:
@ -664,23 +696,40 @@ void BuildSpec16File( FILE *outfile )
/* Output code segment */
fprintf( outfile, "\nstatic struct\n{\n CALLFROM16 call[%d];\n"
" ENTRYPOINT16 entry[%d];\n} Code_Segment = \n{\n {\n",
nTypes, nFuncs );
fprintf( outfile, "\n#include \"pshpack1.h\"\n" );
fprintf( outfile, "\nstatic struct code_segment\n{\n" );
fprintf( outfile, " struct {\n" );
#ifdef __i386__
fprintf( outfile, " unsigned char pushl;\n" ); /* pushl $relay */
fprintf( outfile, " void *relay;\n" );
fprintf( outfile, " unsigned char lcall;\n" ); /* lcall __FLATCS__:glue */
fprintf( outfile, " void *glue;\n" );
fprintf( outfile, " unsigned short flatcs;\n" );
#endif
fprintf( outfile, " unsigned short lret;\n" ); /* lret $args */
fprintf( outfile, " unsigned short args;\n" );
fprintf( outfile, " unsigned int arg_types[2];\n" );
fprintf( outfile, " } call[%d];\n", nTypes );
fprintf( outfile, " struct {\n" );
#ifdef __i386__
fprintf( outfile, " unsigned short pushw_bp;\n" ); /* pushw %bp */
fprintf( outfile, " unsigned char pushl;\n" ); /* pushl $target */
#endif
fprintf( outfile, " void (*target)();\n" );
fprintf( outfile, " unsigned short call;\n" ); /* call CALLFROM16 */
fprintf( outfile, " short callfrom16;\n" );
fprintf( outfile, " } entry[%d];\n", nFuncs );
fprintf( outfile, "} code_segment =\n{\n {\n" );
code_offset = 0;
for ( i = 0; i < nTypes; i++ )
{
char profile[101], *arg;
int argsize = 0;
sprintf( profile, "%s_%s_%s",
(typelist[i]->type == TYPE_CDECL) ? "c" : "p",
(typelist[i]->type == TYPE_REGISTER) ? "regs" :
(typelist[i]->type == TYPE_INTERRUPT) ? "intr" :
(typelist[i]->type == TYPE_PASCAL_16) ? "word" : "long",
typelist[i]->u.func.arg_types );
unsigned int arg_types[2];
int j, argsize = 0;
strcpy( profile, get_function_name( typelist[i] ));
if ( typelist[i]->type != TYPE_CDECL )
for ( arg = typelist[i]->u.func.arg_types; *arg; arg++ )
switch ( *arg )
@ -697,25 +746,46 @@ void BuildSpec16File( FILE *outfile )
break;
}
if ( typelist[i]->type == TYPE_INTERRUPT )
argsize += 2;
if (typelist[i]->flags & FLAG_INTERRUPT) argsize += 2;
/* build the arg types bit fields */
arg_types[0] = arg_types[1] = 0;
for (j = 0; typelist[i]->u.func.arg_types[j]; j++)
{
int type = 0;
switch(typelist[i]->u.func.arg_types[j])
{
case 'w': type = ARG_WORD; break;
case 's': type = ARG_SWORD; break;
case 'l': type = ARG_LONG; break;
case 'p': type = ARG_PTR; break;
case 't': type = ARG_STR; break;
case 'T': type = ARG_SEGSTR; break;
}
arg_types[j / 10] |= type << (3 * (j % 10));
}
if (typelist[i]->flags & (FLAG_REGISTER|FLAG_INTERRUPT)) arg_types[0] |= ARG_REGISTER;
if (typelist[i]->type == TYPE_PASCAL_16) arg_types[0] |= ARG_RET16;
#ifdef __i386__
fprintf( outfile, " { 0x68, %s_CallFrom16_%s, 0x9a, __wine_call_from_16_%s,\n",
DLLName, profile,
(typelist[i]->type == TYPE_REGISTER
|| typelist[i]->type == TYPE_INTERRUPT)? "regs":
(typelist[i]->flags & (FLAG_REGISTER|FLAG_INTERRUPT)) ? "regs":
typelist[i]->type == TYPE_PASCAL_16? "word" : "long" );
if (argsize)
fprintf( outfile, " 0x%04x, 0x66, 0xca, %d, \"%s\" },\n",
code_selector, argsize, profile );
fprintf( outfile, " 0x%04x, 0xca66, %d, { 0x%08x, 0x%08x } },\n",
code_selector, argsize, arg_types[0], arg_types[1] );
else
fprintf( outfile, " 0x%04x, 0x66, 0xcb, 0x9090, \"%s\" },\n",
code_selector, profile );
fprintf( outfile, " 0x%04x, 0xcb66, 0x9090, { 0x%08x, 0x%08x } },\n",
code_selector, arg_types[0], arg_types[1] );
#else
fprintf( outfile, " { \"%s\" },\n", profile );
if (argsize)
fprintf( outfile, " { 0xca66, %d, { 0x%08x, 0x%08x } },\n",
argsize, arg_types[0], arg_types[1] );
else
fprintf( outfile, " { 0xcb66, 0x9090, { 0x%08x, 0x%08x } },\n",
arg_types[0], arg_types[1] );
#endif
code_offset += sizeof(CALLFROM16);
}
fprintf( outfile, " },\n {\n" );
@ -735,8 +805,6 @@ void BuildSpec16File( FILE *outfile )
data_offset += StoreVariableCode( data + data_offset, 4, odp);
break;
case TYPE_REGISTER:
case TYPE_INTERRUPT:
case TYPE_CDECL:
case TYPE_PASCAL:
case TYPE_PASCAL_16:
@ -746,18 +814,14 @@ void BuildSpec16File( FILE *outfile )
fprintf( outfile, " /* %s.%d */ ", DLLName, i );
#ifdef __i386__
fprintf( outfile, "{ 0x5566, 0x68, %s, 0xe866, %d /* %s_%s_%s */ },\n",
fprintf( outfile, "{ 0x5566, 0x68, %s, 0xe866, %d /* %s */ },\n",
#else
fprintf( outfile, "{ %s, %d, /* %s_%s_%s */ },\n",
fprintf( outfile, "{ %s, 0xe866, %d, /* %s */ },\n",
#endif
odp->link_name,
(type-typelist)*sizeof(CALLFROM16) -
(code_offset + sizeof(ENTRYPOINT16)),
(odp->type == TYPE_CDECL) ? "c" : "p",
(odp->type == TYPE_REGISTER) ? "regs" :
(odp->type == TYPE_INTERRUPT) ? "intr" :
(odp->type == TYPE_PASCAL_16) ? "word" : "long",
odp->u.func.arg_types );
get_function_name( odp ) );
odp->offset = code_offset;
code_offset += sizeof(ENTRYPOINT16);
@ -783,10 +847,19 @@ void BuildSpec16File( FILE *outfile )
/* Output the DLL descriptor */
fprintf( outfile, "\nstatic const BUILTIN16_DESCRIPTOR descriptor = \n{\n" );
fprintf( outfile, "#include \"poppack.h\"\n\n" );
fprintf( outfile, "static const struct dll_descriptor\n{\n" );
fprintf( outfile, " unsigned char *module_start;\n" );
fprintf( outfile, " int module_size;\n" );
fprintf( outfile, " struct code_segment *code_start;\n" );
fprintf( outfile, " unsigned char *data_start;\n" );
fprintf( outfile, " const char *owner;\n" );
fprintf( outfile, " const unsigned char *rsrc;\n" );
fprintf( outfile, "} descriptor =\n{\n" );
fprintf( outfile, " Module,\n" );
fprintf( outfile, " sizeof(Module),\n" );
fprintf( outfile, " &Code_Segment,\n" );
fprintf( outfile, " &code_segment,\n" );
fprintf( outfile, " Data_Segment,\n" );
fprintf( outfile, " \"%s\",\n", owner_name );
fprintf( outfile, " %s\n", res_size ? "resource_data" : "0" );
@ -822,6 +895,7 @@ void BuildSpec16File( FILE *outfile )
fprintf( outfile,
"void __wine_spec_%s_init(void)\n"
"{\n"
" extern void __wine_register_dll_16( const struct dll_descriptor *descr );\n"
" __wine_register_dll_16( &descriptor );\n"
"}\n", DLLName );
}
@ -838,12 +912,14 @@ void BuildGlue( FILE *outfile, FILE *infile )
/* File header */
fprintf( outfile, "/* File generated automatically from %s; do not edit! */\n\n",
input_file_name );
fprintf( outfile, "#include \"stackframe.h\"\n\n" );
output_file_header( outfile );
fprintf( outfile, "extern WORD WINAPI wine_call_to_16_word( FARPROC16 target, INT nArgs );\n" );
fprintf( outfile, "extern LONG WINAPI wine_call_to_16_long( FARPROC16 target, INT nArgs );\n" );
#ifdef __i386__
fprintf( outfile, "extern unsigned short __stdcall wine_call_to_16_word( void (*target)(), int args );\n" );
fprintf( outfile, "extern unsigned int __stdcall wine_call_to_16_long( void (*target)(), int args );\n\n" );
#else
fprintf( outfile, "#include <assert.h>\n\n" );
#endif
/* Build the callback glue functions */
@ -853,18 +929,7 @@ void BuildGlue( FILE *outfile, FILE *infile )
}
while (fgets( buffer, sizeof(buffer), infile ))
{
char *p;
if ( (p = strstr( buffer, "CallFrom16_" )) != NULL )
{
char *q, *profile = p + strlen( "CallFrom16_" );
for (q = profile; (*q == '_') || isalpha(*q); q++ )
;
*q = '\0';
for (q = p-1; q > buffer && ((*q == '_') || isalnum(*q)); q-- )
;
if ( ++q < p ) p[-1] = '\0'; else q = "";
BuildCallFrom16Func( outfile, profile, q, FALSE );
}
char *p;
if ( (p = strstr( buffer, "CallTo16_" )) != NULL )
{
char *q, *profile = p + strlen( "CallTo16_" );

View file

@ -159,14 +159,12 @@ static int output_exports( FILE *outfile, int nr_exports )
case TYPE_STDCALL:
case TYPE_VARARGS:
case TYPE_CDECL:
fprintf( outfile, " \"\\t.long " PREFIX "%s\\n\"\n", odp->link_name);
fprintf( outfile, " \"\\t.long " PREFIX "%s\\n\"\n",
(odp->flags & FLAG_REGISTER) ? make_internal_name(odp,"regs") : odp->link_name );
break;
case TYPE_STUB:
fprintf( outfile, " \"\\t.long " PREFIX "%s\\n\"\n", make_internal_name( odp, "stub" ) );
break;
case TYPE_REGISTER:
fprintf( outfile, " \"\\t.long " PREFIX "%s\\n\"\n", make_internal_name( odp, "regs" ) );
break;
case TYPE_VARIABLE:
fprintf( outfile, " \"\\t.long " PREFIX "%s\\n\"\n", make_internal_name( odp, "var" ) );
break;
@ -239,14 +237,13 @@ static int output_exports( FILE *outfile, int nr_exports )
for (i = Base; i <= Limit; i++)
{
ORDDEF *odp = Ordinals[i];
unsigned int j, mask = 0;
unsigned int j, args, mask = 0;
const char *name;
/* skip non-existent entry points */
if (!odp) goto ignore;
/* skip non-functions */
if ((odp->type != TYPE_STDCALL) &&
(odp->type != TYPE_CDECL) &&
(odp->type != TYPE_REGISTER)) goto ignore;
if ((odp->type != TYPE_STDCALL) && (odp->type != TYPE_CDECL)) goto ignore;
/* skip norelay entry points */
if (odp->flags & FLAG_NORELAY) goto ignore;
@ -257,31 +254,26 @@ static int output_exports( FILE *outfile, int nr_exports )
}
if ((odp->flags & FLAG_RET64) && (j < 16)) mask |= 0x80000000;
name = odp->link_name;
args = strlen(odp->u.func.arg_types) * sizeof(int);
if (odp->flags & FLAG_REGISTER)
{
name = make_internal_name( odp, "regs" );
args |= 0x8000;
}
switch(odp->type)
{
case TYPE_STDCALL:
fprintf( outfile, " \"\\tjmp " PREFIX "%s\\n\"\n", odp->link_name );
fprintf( outfile, " \"\\tret $%d\\n\"\n",
strlen(odp->u.func.arg_types) * sizeof(int) );
fprintf( outfile, " \"\\t.long " PREFIX "%s,0x%08x\\n\"\n",
odp->link_name, mask );
fprintf( outfile, " \"\\tjmp " PREFIX "%s\\n\"\n", name );
fprintf( outfile, " \"\\tret $0x%04x\\n\"\n", args );
fprintf( outfile, " \"\\t.long " PREFIX "%s,0x%08x\\n\"\n", name, mask );
break;
case TYPE_CDECL:
fprintf( outfile, " \"\\tjmp " PREFIX "%s\\n\"\n", odp->link_name );
fprintf( outfile, " \"\\tjmp " PREFIX "%s\\n\"\n", name );
fprintf( outfile, " \"\\tret\\n\"\n" );
fprintf( outfile, " \"\\t.short %d\\n\"\n",
strlen(odp->u.func.arg_types) * sizeof(int) );
fprintf( outfile, " \"\\t.long " PREFIX "%s,0x%08x\\n\"\n",
odp->link_name, mask );
break;
case TYPE_REGISTER:
fprintf( outfile, " \"\\tjmp " PREFIX "%s\\n\"\n",
make_internal_name( odp, "regs" ) );
fprintf( outfile, " \"\\tret\\n\"\n" );
fprintf( outfile, " \"\\t.short 0x%04x\\n\"\n",
0x8000 | strlen(odp->u.func.arg_types) * sizeof(int) );
fprintf( outfile, " \"\\t.long " PREFIX "%s,0x%08x\\n\"\n",
make_internal_name( odp, "regs" ), mask );
fprintf( outfile, " \"\\t.short 0x%04x\\n\"\n", args );
fprintf( outfile, " \"\\t.long " PREFIX "%s,0x%08x\\n\"\n", name, mask );
break;
default:
assert(0);
@ -401,7 +393,8 @@ static void output_register_funcs( FILE *outfile )
for (i = 0; i < nb_entry_points; i++)
{
ORDDEF *odp = EntryPoints[i];
if (odp->type != TYPE_REGISTER) continue;
if (odp->type != TYPE_STDCALL && odp->type != TYPE_CDECL) continue;
if (!(odp->flags & FLAG_REGISTER)) continue;
name = make_internal_name( odp, "regs" );
fprintf( outfile,
"asm(\".align %d\\n\\t\"\n"
@ -412,7 +405,8 @@ static void output_register_funcs( FILE *outfile )
" \".byte %d,%d\");\n",
get_alignment(4),
name, name, odp->link_name,
4 * strlen(odp->u.func.arg_types), 4 * strlen(odp->u.func.arg_types) );
strlen(odp->u.func.arg_types) * sizeof(int),
(odp->type == TYPE_CDECL) ? 0 : (strlen(odp->u.func.arg_types) * sizeof(int)) );
}
}