Commit 1a0f2863 authored by Alexandre Julliard's avatar Alexandre Julliard

Moved all 16-bit relay code to the text section.

Changed a few symbol names for better consistency.
parent 84f9d136
......@@ -224,6 +224,8 @@ extern HTASK16 TASK_GetTaskFromThread( DWORD thread );
extern TDB *TASK_GetCurrent(void);
extern void TASK_InstallTHHook( THHOOK *pNewThook );
extern DWORD CallTo16_DataSelector;
extern DWORD CallTo16_TebSelector;
extern SEGPTR CALL32_CBClient_RetAddr;
extern SEGPTR CALL32_CBClientEx_RetAddr;
......
......@@ -30,6 +30,7 @@
#include "winternl.h"
#include "wine/winbase16.h"
#include "kernel_private.h"
#include "kernel16_private.h"
#include "wine/library.h"
#include "wine/debug.h"
......@@ -44,10 +45,6 @@ static CRITICAL_SECTION_DEBUG critsect_debug =
};
static SYSLEVEL Win16Mutex = { { &critsect_debug, -1, 0, 0, 0, 0 }, 1 };
#ifdef __i386__
extern unsigned int CallTo16_TebSelector;
#endif
/************************************************************************
* GetpWin16Lock (KERNEL32.93)
......
......@@ -76,22 +76,19 @@ static DWORD CALLBACK start_thread16( LPVOID threadArgs )
/* symbols exported from relay16.s */
extern DWORD WINAPI wine_call_to_16( FARPROC16 target, DWORD cbArgs, PEXCEPTION_HANDLER handler );
extern void WINAPI wine_call_to_16_regs( CONTEXT86 *context, DWORD cbArgs, PEXCEPTION_HANDLER handler );
extern void Call16_Ret_Start();
extern void Call16_Ret_End();
extern void CallTo16_Ret();
extern void __wine_call_to_16_ret(void);
extern void CALL32_CBClient_Ret();
extern void CALL32_CBClientEx_Ret();
extern void DPMI_PendingEventCheck();
extern void DPMI_PendingEventCheck_Cleanup();
extern void DPMI_PendingEventCheck_Return();
extern DWORD CallTo16_DataSelector;
extern BYTE Call16_Start;
extern BYTE Call16_End;
extern BYTE __wine_call16_start[];
extern BYTE __wine_call16_end[];
extern void RELAY16_InitDebugLists(void);
static LONG CALLBACK vectored_handler( EXCEPTION_POINTERS *ptrs );
static SEGPTR call16_ret_addr; /* segptr to CallTo16_Ret routine */
static SEGPTR call16_ret_addr; /* segptr to __wine_call_to_16_ret routine */
static WORD dpmi_checker_selector;
static DWORD dpmi_checker_offset_call;
......@@ -104,28 +101,29 @@ static DWORD dpmi_checker_offset_return;
BOOL WOWTHUNK_Init(void)
{
/* allocate the code selector for CallTo16 routines */
WORD codesel = SELECTOR_AllocBlock( (void *)Call16_Ret_Start,
(char *)Call16_Ret_End - (char *)Call16_Ret_Start,
WINE_LDT_FLAGS_CODE | WINE_LDT_FLAGS_32BIT );
LDT_ENTRY entry;
WORD codesel = wine_ldt_alloc_entries(1);
if (!codesel) return FALSE;
wine_ldt_set_base( &entry, __wine_call16_start );
wine_ldt_set_limit( &entry, (BYTE *)(&CallTo16_TebSelector + 1) - __wine_call16_start - 1 );
wine_ldt_set_flags( &entry, WINE_LDT_FLAGS_CODE | WINE_LDT_FLAGS_32BIT );
wine_ldt_set_entry( codesel, &entry );
/* Patch the return addresses for CallTo16 routines */
CallTo16_DataSelector = wine_get_ds();
call16_ret_addr = MAKESEGPTR( codesel, (char*)CallTo16_Ret - (char*)Call16_Ret_Start );
call16_ret_addr = MAKESEGPTR( codesel, (BYTE *)__wine_call_to_16_ret - __wine_call16_start );
CALL32_CBClient_RetAddr =
MAKESEGPTR( codesel, (char*)CALL32_CBClient_Ret - (char*)Call16_Ret_Start );
MAKESEGPTR( codesel, (BYTE *)CALL32_CBClient_Ret - __wine_call16_start );
CALL32_CBClientEx_RetAddr =
MAKESEGPTR( codesel, (char*)CALL32_CBClientEx_Ret - (char*)Call16_Ret_Start );
MAKESEGPTR( codesel, (BYTE *)CALL32_CBClientEx_Ret - __wine_call16_start );
/* Prepare selector and offsets for DPMI event checking. */
dpmi_checker_selector = codesel;
dpmi_checker_offset_call =
(char*)DPMI_PendingEventCheck - (char*)Call16_Ret_Start;
dpmi_checker_offset_cleanup =
(char*)DPMI_PendingEventCheck_Cleanup - (char*)Call16_Ret_Start;
dpmi_checker_offset_return =
(char*)DPMI_PendingEventCheck_Return - (char*)Call16_Ret_Start;
dpmi_checker_offset_call = (BYTE *)DPMI_PendingEventCheck - __wine_call16_start;
dpmi_checker_offset_cleanup = (BYTE *)DPMI_PendingEventCheck_Cleanup - __wine_call16_start;
dpmi_checker_offset_return = (BYTE *)DPMI_PendingEventCheck_Return - __wine_call16_start;
if (TRACE_ON(relay) || TRACE_ON(snoop)) RELAY16_InitDebugLists();
......@@ -146,7 +144,7 @@ static BOOL fix_selector( CONTEXT *context )
WORD *stack;
BYTE *instr = (BYTE *)context->Eip;
if (instr < &Call16_Start || instr >= &Call16_End) return FALSE;
if (instr < __wine_call16_start || instr >= __wine_call16_end) return FALSE;
/* skip prefixes */
while (*instr == 0x66 || *instr == 0x67) instr++;
......
......@@ -611,7 +611,7 @@ static void BuildCallTo16Core( FILE *outfile, int reg_func )
*/
static void BuildRet16Func( FILE *outfile )
{
function_header( outfile, "CallTo16_Ret" );
function_header( outfile, "__wine_call_to_16_ret" );
/* Save %esp into %esi */
fprintf( outfile, "\tmovl %%esp,%%esi\n" );
......@@ -619,12 +619,12 @@ static void BuildRet16Func( FILE *outfile )
/* Restore 32-bit segment registers */
fprintf( outfile, "\t.byte 0x2e\n\tmovl %s", asm_name("CallTo16_DataSelector") );
fprintf( outfile, "-%s,%%edi\n", asm_name("Call16_Ret_Start") );
fprintf( outfile, "-%s,%%edi\n", asm_name("__wine_call16_start") );
fprintf( outfile, "%s\tmovw %%di,%%ds\n", data16_prefix() );
fprintf( outfile, "%s\tmovw %%di,%%es\n", data16_prefix() );
fprintf( outfile, "\t.byte 0x2e\n\tmov %s", asm_name("CallTo16_TebSelector") );
fprintf( outfile, "-%s,%%fs\n", asm_name("Call16_Ret_Start") );
fprintf( outfile, "-%s,%%fs\n", asm_name("__wine_call16_start") );
fprintf( outfile, "\t.byte 0x64\n\tmov (%d),%%gs\n", STRUCTOFFSET(TEB,gs_sel) );
......@@ -636,17 +636,7 @@ static void BuildRet16Func( FILE *outfile )
/* Return to caller */
fprintf( outfile, "\tlret\n" );
/* Function footer */
function_footer( outfile, "CallTo16_Ret" );
/* Declare the return address and data selector variables */
fprintf( outfile, "\n\t.align %d\n", get_alignment(4) );
fprintf( outfile, "\t.globl %s\n", asm_name("CallTo16_DataSelector") );
fprintf( outfile, "%s:\t.long 0\n", asm_name("CallTo16_DataSelector") );
fprintf( outfile, "\t.globl %s\n", asm_name("CallTo16_TebSelector") );
fprintf( outfile, "%s:\t.long 0\n", asm_name("CallTo16_TebSelector") );
function_footer( outfile, "__wine_call_to_16_ret" );
}
......@@ -742,13 +732,7 @@ static void BuildRet16Func( FILE *outfile )
*/
static void BuildCallTo32CBClient( FILE *outfile, BOOL isEx )
{
const char *name = isEx? "CALL32_CBClientEx" : "CALL32_CBClient";
/* Function header */
fprintf( outfile, "\n\t.align %d\n", get_alignment(4) );
fprintf( outfile, "\t.globl %s\n", asm_name(name) );
fprintf( outfile, "%s:\n", asm_name(name) );
function_header( outfile, isEx ? "CALL32_CBClientEx" : "CALL32_CBClient" );
/* Entry code */
......@@ -798,18 +782,11 @@ static void BuildCallTo32CBClient( FILE *outfile, BOOL isEx )
fprintf( outfile, "\tpopl %%edi\n" );
fprintf( outfile, "\tpopl %%ebp\n" );
fprintf( outfile, "\tret\n" );
function_footer( outfile, name );
}
static void BuildCallTo32CBClientRet( FILE *outfile, BOOL isEx )
{
const char *name = isEx? "CALL32_CBClientEx_Ret" : "CALL32_CBClient_Ret";
function_footer( outfile, isEx ? "CALL32_CBClientEx" : "CALL32_CBClient" );
/* '16-bit' return stub */
fprintf( outfile, "\n\t.globl %s\n", asm_name(name) );
fprintf( outfile, "%s:\n", asm_name(name) );
function_header( outfile, isEx ? "CALL32_CBClientEx_Ret" : "CALL32_CBClient_Ret" );
if ( !isEx )
{
fprintf( outfile, "\tmovzwl %%sp, %%ebx\n" );
......@@ -823,7 +800,7 @@ static void BuildCallTo32CBClientRet( FILE *outfile, BOOL isEx )
fprintf( outfile, "\tlssl %%ss:-12(%%ebx), %%esp\n" );
}
fprintf( outfile, "\tlret\n" );
function_footer( outfile, name );
function_footer( outfile, isEx ? "CALL32_CBClientEx_Ret" : "CALL32_CBClient_Ret" );
}
......@@ -1032,9 +1009,8 @@ void BuildRelays16( FILE *outfile )
fprintf( outfile, "%s:\n\n", asm_name("__wine_spec_thunk_text_16") );
fprintf( outfile, "\t.globl %s\n", asm_name("Call16_Start") );
fprintf( outfile, "%s:\n", asm_name("Call16_Start") );
fprintf( outfile, "\t.byte 0\n\n" );
fprintf( outfile, "\t.globl %s\n", asm_name("__wine_call16_start") );
fprintf( outfile, "%s:\n", asm_name("__wine_call16_start") );
/* Standard CallFrom16 routine (WORD return) */
BuildCallFrom16Core( outfile, FALSE, FALSE, TRUE );
......@@ -1054,38 +1030,28 @@ void BuildRelays16( FILE *outfile )
/* Register CallTo16 routine */
BuildCallTo16Core( outfile, 1 );
/* Standard CallTo16 return stub */
BuildRet16Func( outfile );
/* CBClientThunkSL routine */
BuildCallTo32CBClient( outfile, FALSE );
/* CBClientThunkSLEx routine */
BuildCallTo32CBClient( outfile, TRUE );
fprintf( outfile, "\t.globl %s\n", asm_name("Call16_End") );
fprintf( outfile, "%s:\n", asm_name("Call16_End") );
function_footer( outfile, "__wine_spec_thunk_text_16" );
/* The whole Call16_Ret segment must lie within the .data section */
fprintf( outfile, "\n\t.data\n" );
fprintf( outfile, "%s:\n\n", asm_name("__wine_spec_thunk_data_16") );
fprintf( outfile, "\t.globl %s\n", asm_name("Call16_Ret_Start") );
fprintf( outfile, "%s:\n", asm_name("Call16_Ret_Start") );
/* Standard CallTo16 return stub */
BuildRet16Func( outfile );
/* CBClientThunkSL return stub */
BuildCallTo32CBClientRet( outfile, FALSE );
/* CBClientThunkSLEx return stub */
BuildCallTo32CBClientRet( outfile, TRUE );
/* Pending DPMI events check stub */
BuildPendingEventCheck( outfile );
/* End of Call16_Ret segment */
fprintf( outfile, "\n\t.globl %s\n", asm_name("Call16_Ret_End") );
fprintf( outfile, "%s:\n", asm_name("Call16_Ret_End") );
function_footer( outfile, "__wine_spec_thunk_data_16" );
fprintf( outfile, "\t.globl %s\n", asm_name("__wine_call16_end") );
fprintf( outfile, "%s:\n", asm_name("__wine_call16_end") );
function_footer( outfile, "__wine_spec_thunk_text_16" );
/* Declare the return address and data selector variables */
fprintf( outfile, "\n\t.data\n\t.align %d\n", get_alignment(4) );
fprintf( outfile, "\t.globl %s\n", asm_name("CallTo16_DataSelector") );
fprintf( outfile, "%s:\t.long 0\n", asm_name("CallTo16_DataSelector") );
fprintf( outfile, "\t.globl %s\n", asm_name("CallTo16_TebSelector") );
fprintf( outfile, "%s:\t.long 0\n", asm_name("CallTo16_TebSelector") );
}
/*******************************************************************
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment