Jacek Caban : ntdll: Store all non-volatile i386 registers in syscall dispatcher.

Alexandre Julliard julliard at winehq.org
Thu Feb 25 16:45:38 CST 2021


Module: wine
Branch: master
Commit: b04f2689a2b87c657781c0b6ddad16c73348ddb1
URL:    https://source.winehq.org/git/wine.git/?a=commit;h=b04f2689a2b87c657781c0b6ddad16c73348ddb1

Author: Jacek Caban <jacek at codeweavers.com>
Date:   Thu Feb 25 18:53:56 2021 +0100

ntdll: Store all non-volatile i386 registers in syscall dispatcher.

Signed-off-by: Jacek Caban <jacek at codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard at winehq.org>

---

 dlls/ntdll/unix/signal_i386.c | 29 ++++++++++++++---------------
 tools/winebuild/import.c      | 13 ++++++++++++-
 2 files changed, 26 insertions(+), 16 deletions(-)

diff --git a/dlls/ntdll/unix/signal_i386.c b/dlls/ntdll/unix/signal_i386.c
index 6c46c615f56..be3f1060e4a 100644
--- a/dlls/ntdll/unix/signal_i386.c
+++ b/dlls/ntdll/unix/signal_i386.c
@@ -479,10 +479,10 @@ struct syscall_frame
     DWORD              edi;     /* 28 */
     DWORD              esi;     /* 2c */
     DWORD              ebp;     /* 30 */
-    DWORD              thunk_addr;
-    DWORD              ret_addr;
 };
 
+C_ASSERT( sizeof(struct syscall_frame) == 0x34 );
+
 struct x86_thread_data
 {
     DWORD              fs;            /* 1d4 TEB selector */
@@ -1314,20 +1314,20 @@ NTSTATUS WINAPI NtGetContextThread( HANDLE handle, CONTEXT *context )
         }
         if (needed_flags & CONTEXT_CONTROL)
         {
-            context->Esp    = (DWORD)&frame->ret_addr;
+            context->Esp    = frame->esp;
             context->Ebp    = frame->ebp;
-            context->Eip    = frame->thunk_addr;
-            context->EFlags = 0x202;
-            context->SegCs  = get_cs();
-            context->SegSs  = get_ds();
+            context->Eip    = frame->eip;
+            context->EFlags = frame->eflags;
+            context->SegCs  = frame->cs;
+            context->SegSs  = frame->ds;
             context->ContextFlags |= CONTEXT_CONTROL;
         }
         if (needed_flags & CONTEXT_SEGMENTS)
         {
-            context->SegDs = get_ds();
-            context->SegEs = get_ds();
-            context->SegFs = get_fs();
-            context->SegGs = get_gs();
+            context->SegDs = frame->ds;
+            context->SegEs = frame->es;
+            context->SegFs = frame->fs;
+            context->SegGs = frame->gs;
             context->ContextFlags |= CONTEXT_SEGMENTS;
         }
         if (needed_flags & CONTEXT_FLOATING_POINT) save_fpu( context );
@@ -1732,7 +1732,6 @@ struct apc_stack_layout * WINAPI setup_user_apc_dispatcher_stack( CONTEXT *conte
 }
 
 C_ASSERT( sizeof(struct apc_stack_layout) == 0x2e0 );
-C_ASSERT( offsetof(struct syscall_frame, ret_addr) == 0x38 );
 C_ASSERT( offsetof(struct apc_stack_layout, context) == 20 );
 
 /***********************************************************************
@@ -1916,14 +1915,14 @@ static BOOL handle_syscall_fault( ucontext_t *sigcontext, void *stack_ptr,
     }
     else
     {
-        TRACE( "returning to user mode ip=%08x ret=%08x\n", frame->ret_addr, rec->ExceptionCode );
+        TRACE( "returning to user mode ip=%08x ret=%08x\n", frame->eip, rec->ExceptionCode );
         EAX_sig(sigcontext) = rec->ExceptionCode;
         EBX_sig(sigcontext) = frame->ebx;
         ESI_sig(sigcontext) = frame->esi;
         EDI_sig(sigcontext) = frame->edi;
         EBP_sig(sigcontext) = frame->ebp;
-        ESP_sig(sigcontext) = (DWORD)&frame->ret_addr;
-        EIP_sig(sigcontext) = frame->thunk_addr;
+        ESP_sig(sigcontext) = frame->esp;
+        EIP_sig(sigcontext) = frame->eip;
         x86_thread_data()->syscall_frame = NULL;
     }
     return TRUE;
diff --git a/tools/winebuild/import.c b/tools/winebuild/import.c
index 8620e9be479..720cf0589fd 100644
--- a/tools/winebuild/import.c
+++ b/tools/winebuild/import.c
@@ -1438,13 +1438,24 @@ static void output_syscall_dispatcher( int count, const char *variant )
         output_cfi( ".cfi_rel_offset %%ebp,0\n" );
         output( "\tmovl %%esp,%%ebp\n" );
         output_cfi( ".cfi_def_cfa_register %%ebp\n" );
-        output( "\tsubl $0x30,%%esp\n" );
+        output( "\tleal -0x2c(%%esp),%%esp\n" );
         output( "\tmovl %%ebx,-0x14(%%ebp)\n" );
         output_cfi( ".cfi_rel_offset %%ebx,-0x14\n" );
         output( "\tmovl %%edi,-0x08(%%ebp)\n" );
         output_cfi( ".cfi_rel_offset %%edi,-0x08\n" );
         output( "\tmovl %%esi,-0x04(%%ebp)\n" );
         output_cfi( ".cfi_rel_offset %%esi,-0x04\n" );
+        output( "\tpushfl\n" );
+        output( "\tmovw %%gs,-0x1a(%%ebp)\n" );
+        output( "\tmovw %%fs,-0x1c(%%ebp)\n" );
+        output( "\tmovw %%es,-0x1e(%%ebp)\n" );
+        output( "\tmovw %%ds,-0x20(%%ebp)\n" );
+        output( "\tmovw %%ss,-0x22(%%ebp)\n" );
+        output( "\tmovw %%cs,-0x24(%%ebp)\n" );
+        output( "\tleal 8(%%ebp),%%ecx\n" );
+        output( "\tmovl %%ecx,-0x28(%%ebp)\n" ); /* frame->esp */
+        output( "\tmovl 4(%%ebp),%%ecx\n" );
+        output( "\tmovl %%ecx,-0x2c(%%ebp)\n" ); /* frame->eip */
         output( "\tmovl %%esp,%%fs:0x1f8\n" );  /* x86_thread_data()->syscall_frame */
         output( "\tcmpl $%u,%%eax\n", count );
         output( "\tjae 3f\n" );




More information about the wine-cvs mailing list