Alexandre Julliard : ntdll: Always restore the context after an exception even if setting the debug registers fails .
Alexandre Julliard
julliard at winehq.org
Fri Mar 5 09:42:54 CST 2010
Module: wine
Branch: master
Commit: c09df80620fe33f7f0de6eb7f19d20792f2c4774
URL: http://source.winehq.org/git/wine.git/?a=commit;h=c09df80620fe33f7f0de6eb7f19d20792f2c4774
Author: Alexandre Julliard <julliard at winehq.org>
Date: Fri Mar 5 12:25:34 2010 +0100
ntdll: Always restore the context after an exception even if setting the debug registers fails.
---
dlls/ntdll/signal_i386.c | 45 +++++++++++++++++++++++++++++++++++++++------
1 files changed, 39 insertions(+), 6 deletions(-)
diff --git a/dlls/ntdll/signal_i386.c b/dlls/ntdll/signal_i386.c
index 4eccb61..4998820 100644
--- a/dlls/ntdll/signal_i386.c
+++ b/dlls/ntdll/signal_i386.c
@@ -1188,6 +1188,35 @@ void set_cpu_context( const CONTEXT *context )
/***********************************************************************
+ * set_debug_registers
+ */
+static void set_debug_registers( const CONTEXT *context )
+{
+ DWORD flags = context->ContextFlags & ~CONTEXT_i386;
+ context_t server_context;
+
+ if (!(flags & CONTEXT_DEBUG_REGISTERS)) return;
+ if (ntdll_get_thread_data()->dr0 == context->Dr0 &&
+ ntdll_get_thread_data()->dr1 == context->Dr1 &&
+ ntdll_get_thread_data()->dr2 == context->Dr2 &&
+ ntdll_get_thread_data()->dr3 == context->Dr3 &&
+ ntdll_get_thread_data()->dr6 == context->Dr6 &&
+ ntdll_get_thread_data()->dr7 == context->Dr7) return;
+
+ context_to_server( &server_context, context );
+
+ SERVER_START_REQ( set_thread_context )
+ {
+ req->handle = wine_server_obj_handle( GetCurrentThread() );
+ req->suspend = 0;
+ wine_server_add_data( req, &server_context, sizeof(server_context) );
+ wine_server_call( req );
+ }
+ SERVER_END_REQ;
+}
+
+
+/***********************************************************************
* copy_context
*
* Copy a register context according to the flags.
@@ -1678,9 +1707,9 @@ static void WINAPI raise_segv_exception( EXCEPTION_RECORD *rec, CONTEXT *context
break;
}
status = NtRaiseException( rec, context, TRUE );
- if (status) raise_status( status, rec );
+ raise_status( status, rec );
done:
- NtSetContextThread( GetCurrentThread(), context );
+ set_cpu_context( context );
}
@@ -1709,7 +1738,7 @@ static void WINAPI raise_trap_exception( EXCEPTION_RECORD *rec, CONTEXT *context
}
status = NtRaiseException( rec, context, TRUE );
- if (status) raise_status( status, rec );
+ raise_status( status, rec );
}
@@ -1723,7 +1752,7 @@ static void WINAPI raise_generic_exception( EXCEPTION_RECORD *rec, CONTEXT *cont
NTSTATUS status;
status = NtRaiseException( rec, context, TRUE );
- if (status) raise_status( status, rec );
+ raise_status( status, rec );
}
@@ -1755,7 +1784,7 @@ static void WINAPI raise_vm86_sti_exception( EXCEPTION_RECORD *rec, CONTEXT *con
NtRaiseException( rec, context, TRUE );
}
done:
- NtSetContextThread( GetCurrentThread(), context );
+ set_cpu_context( context );
}
@@ -2345,7 +2374,11 @@ DEFINE_REGS_ENTRYPOINT( RtlUnwind, 4 )
NTSTATUS WINAPI NtRaiseException( EXCEPTION_RECORD *rec, CONTEXT *context, BOOL first_chance )
{
NTSTATUS status = raise_exception( rec, context, first_chance );
- if (status == STATUS_SUCCESS) NtSetContextThread( GetCurrentThread(), context );
+ if (status == STATUS_SUCCESS)
+ {
+ set_debug_registers( context );
+ set_cpu_context( context );
+ }
return status;
}
More information about the wine-cvs
mailing list