Rémi Bernon : ntdll: Reimplement DbgPrint* using DBG_PRINTEXCEPTION_C.
Alexandre Julliard
julliard at winehq.org
Fri Nov 20 14:54:32 CST 2020
Module: wine
Branch: master
Commit: c5129d6fc083514bf7b854d3403148627fe66475
URL: https://source.winehq.org/git/wine.git/?a=commit;h=c5129d6fc083514bf7b854d3403148627fe66475
Author: Rémi Bernon <rbernon at codeweavers.com>
Date: Thu Nov 19 10:25:22 2020 +0100
ntdll: Reimplement DbgPrint* using DBG_PRINTEXCEPTION_C.
Signed-off-by: Rémi Bernon <rbernon at codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard at winehq.org>
---
dlls/ntdll/rtl.c | 56 +++++++++++++++++++++++++++++++++++---------------
dlls/ntdll/tests/rtl.c | 14 ++++++-------
2 files changed, 46 insertions(+), 24 deletions(-)
diff --git a/dlls/ntdll/rtl.c b/dlls/ntdll/rtl.c
index ca4fea84209..11dbc63a3b3 100644
--- a/dlls/ntdll/rtl.c
+++ b/dlls/ntdll/rtl.c
@@ -39,6 +39,7 @@
#include "ddk/ntddk.h"
WINE_DEFAULT_DEBUG_CHANNEL(ntdll);
+WINE_DECLARE_DEBUG_CHANNEL(debugstr);
/* CRC polynomial 0xedb88320 */
static const DWORD CRC_table[256] =
@@ -297,21 +298,24 @@ void WINAPI RtlDumpResource(LPRTL_RWLOCK rwl)
* misc functions
*/
+static LONG WINAPI debug_exception_handler( EXCEPTION_POINTERS *eptr )
+{
+ EXCEPTION_RECORD *rec = eptr->ExceptionRecord;
+ return (rec->ExceptionCode == DBG_PRINTEXCEPTION_C) ? EXCEPTION_EXECUTE_HANDLER : EXCEPTION_CONTINUE_SEARCH;
+}
+
/******************************************************************************
* DbgPrint [NTDLL.@]
*/
NTSTATUS WINAPIV DbgPrint(LPCSTR fmt, ...)
{
- char buf[512];
- __ms_va_list args;
-
- __ms_va_start(args, fmt);
- _vsnprintf(buf, sizeof(buf), fmt, args);
- __ms_va_end(args);
+ NTSTATUS ret;
+ __ms_va_list args;
- MESSAGE("DbgPrint says: %s",buf);
- /* hmm, raise exception? */
- return STATUS_SUCCESS;
+ __ms_va_start(args, fmt);
+ ret = vDbgPrintEx(0, DPFLTR_ERROR_LEVEL, fmt, args);
+ __ms_va_end(args);
+ return ret;
}
@@ -342,18 +346,36 @@ NTSTATUS WINAPI vDbgPrintEx( ULONG id, ULONG level, LPCSTR fmt, __ms_va_list arg
*/
NTSTATUS WINAPI vDbgPrintExWithPrefix( LPCSTR prefix, ULONG id, ULONG level, LPCSTR fmt, __ms_va_list args )
{
- char buf[1024];
+ ULONG level_mask = level <= 31 ? (1 << level) : level;
+ SIZE_T len = strlen( prefix );
+ char buf[1024], *end;
- _vsnprintf(buf, sizeof(buf), fmt, args);
+ strcpy( buf, prefix );
+ len += _vsnprintf( buf + len, sizeof(buf) - len, fmt, args );
+ end = buf + len - 1;
- switch (level & DPFLTR_MASK)
+ WARN_(debugstr)(*end == '\n' ? "%08x:%08x: %s" : "%08x:%08x: %s\n", id, level_mask, buf);
+
+ if (level_mask & (1 << DPFLTR_ERROR_LEVEL) && NtCurrentTeb()->Peb->BeingDebugged)
{
- case DPFLTR_ERROR_LEVEL: ERR("%s%x: %s", prefix, id, buf); break;
- case DPFLTR_WARNING_LEVEL: WARN("%s%x: %s", prefix, id, buf); break;
- case DPFLTR_TRACE_LEVEL:
- case DPFLTR_INFO_LEVEL:
- default: TRACE("%s%x: %s", prefix, id, buf); break;
+ __TRY
+ {
+ EXCEPTION_RECORD record;
+ record.ExceptionCode = DBG_PRINTEXCEPTION_C;
+ record.ExceptionFlags = 0;
+ record.ExceptionRecord = NULL;
+ record.ExceptionAddress = RtlRaiseException;
+ record.NumberParameters = 2;
+ record.ExceptionInformation[1] = (ULONG_PTR)buf;
+ record.ExceptionInformation[0] = strlen( buf ) + 1;
+ RtlRaiseException( &record );
+ }
+ __EXCEPT(debug_exception_handler)
+ {
+ }
+ __ENDTRY
}
+
return STATUS_SUCCESS;
}
diff --git a/dlls/ntdll/tests/rtl.c b/dlls/ntdll/tests/rtl.c
index 6121dc9f9d0..ae8170f41fe 100644
--- a/dlls/ntdll/tests/rtl.c
+++ b/dlls/ntdll/tests/rtl.c
@@ -3541,19 +3541,19 @@ static void test_DbgPrint(void)
test_dbg_print_except_ret = (LONG)EXCEPTION_EXECUTE_HANDLER;
status = DbgPrint( "test_DbgPrint: %s", "Hello World" );
ok( !status, "DbgPrint returned %x\n", status );
- todo_wine ok( test_dbg_print_except, "DBG_PRINTEXCEPTION_C not received\n" );
+ ok( test_dbg_print_except, "DBG_PRINTEXCEPTION_C not received\n" );
test_dbg_print_except = FALSE;
test_dbg_print_except_ret = (LONG)EXCEPTION_CONTINUE_EXECUTION;
status = DbgPrint( "test_DbgPrint: %s", "Hello World" );
ok( !status, "DbgPrint returned %x\n", status );
- todo_wine ok( test_dbg_print_except, "DBG_PRINTEXCEPTION_C not received\n" );
+ ok( test_dbg_print_except, "DBG_PRINTEXCEPTION_C not received\n" );
test_dbg_print_except = FALSE;
test_dbg_print_except_ret = (LONG)EXCEPTION_CONTINUE_SEARCH;
status = DbgPrint( "test_DbgPrint: %s", "Hello World" );
ok( !status, "DbgPrint returned %x\n", status );
- todo_wine ok( test_dbg_print_except, "DBG_PRINTEXCEPTION_C not received\n" );
+ ok( test_dbg_print_except, "DBG_PRINTEXCEPTION_C not received\n" );
/* FIXME: NtSetDebugFilterState / DbgSetDebugFilterState are probably what's controlling these */
@@ -3562,7 +3562,7 @@ static void test_DbgPrint(void)
test_dbg_print_except_ret = (LONG)EXCEPTION_EXECUTE_HANDLER;
status = DbgPrintEx( 0, DPFLTR_ERROR_LEVEL, "test_DbgPrint: %s", "Hello World" );
ok( !status, "DbgPrintEx returned %x\n", status );
- todo_wine ok( test_dbg_print_except, "DBG_PRINTEXCEPTION_C not received\n" );
+ ok( test_dbg_print_except, "DBG_PRINTEXCEPTION_C not received\n" );
test_dbg_print_except = FALSE;
test_dbg_print_except_ret = (LONG)EXCEPTION_EXECUTE_HANDLER;
@@ -3574,7 +3574,7 @@ static void test_DbgPrint(void)
test_dbg_print_except_ret = (LONG)EXCEPTION_EXECUTE_HANDLER;
status = DbgPrintEx( 0, DPFLTR_MASK|(1 << DPFLTR_ERROR_LEVEL), "test_DbgPrint: %s", "Hello World" );
ok( !status, "DbgPrintEx returned %x\n", status );
- todo_wine ok( test_dbg_print_except, "DBG_PRINTEXCEPTION_C not received\n" );
+ ok( test_dbg_print_except, "DBG_PRINTEXCEPTION_C not received\n" );
test_dbg_print_except = FALSE;
test_dbg_print_except_ret = (LONG)EXCEPTION_EXECUTE_HANDLER;
@@ -3587,13 +3587,13 @@ static void test_DbgPrint(void)
test_dbg_print_except_ret = (LONG)EXCEPTION_EXECUTE_HANDLER;
status = test_vDbgPrintEx( 0, 0xFFFFFFFF, "test_DbgPrint: %s", "Hello World" );
ok( !status, "vDbgPrintEx returned %x\n", status );
- todo_wine ok( test_dbg_print_except, "DBG_PRINTEXCEPTION_C not received\n" );
+ ok( test_dbg_print_except, "DBG_PRINTEXCEPTION_C not received\n" );
test_dbg_print_except = FALSE;
test_dbg_print_except_ret = (LONG)EXCEPTION_EXECUTE_HANDLER;
status = test_vDbgPrintExWithPrefix( "test_", 0, 0xFFFFFFFF, "DbgPrint: %s", "Hello World" );
ok( !status, "vDbgPrintExWithPrefix returned %x\n", status );
- todo_wine ok( test_dbg_print_except, "DBG_PRINTEXCEPTION_C not received\n" );
+ ok( test_dbg_print_except, "DBG_PRINTEXCEPTION_C not received\n" );
Peb->BeingDebugged = debugged;
RtlRemoveVectoredExceptionHandler( handler );
More information about the wine-cvs
mailing list