From: Eric Pouech epouech@codeweavers.com
This mainly allows Wine to reset the tty settings upon termination and not let gdb do it (cf bug report).
Change: user is now required to explicitely terminate gdb ('quit' command) upon debuggee termination.
Wine-Bugs: https://bugs.winehq.org/show_bug.cgi?id=56032
Signed-off-by: Eric Pouech epouech@codeweavers.com --- programs/winedbg/gdbproxy.c | 29 ++++++++++++++++------------- 1 file changed, 16 insertions(+), 13 deletions(-)
diff --git a/programs/winedbg/gdbproxy.c b/programs/winedbg/gdbproxy.c index 238eecb1538..2b750193a44 100644 --- a/programs/winedbg/gdbproxy.c +++ b/programs/winedbg/gdbproxy.c @@ -64,6 +64,7 @@ struct reply_buffer struct gdb_context { /* gdb information */ + HANDLE gdb_ctrl_thread; SOCKET sock; /* incoming buffer */ char* in_buf; @@ -2391,10 +2392,15 @@ static int fetch_data(struct gdb_context* gdbctx) return gdbctx->in_len - in_len; }
+static DWORD WINAPI gdb_ctrl_thread(void *pmt) +{ + return __wine_unix_spawnvp( (char **)pmt, TRUE ); +} + #define FLAG_NO_START 1 #define FLAG_WITH_XTERM 2
-static BOOL gdb_exec(unsigned port, unsigned flags) +static HANDLE gdb_exec(unsigned port, unsigned flags) { WCHAR tmp[MAX_PATH], buf[MAX_PATH]; const char *argv[6]; @@ -2405,7 +2411,7 @@ static BOOL gdb_exec(unsigned port, unsigned flags) if (!(gdb_path = getenv("WINE_GDB"))) gdb_path = "gdb"; GetTempPathW( MAX_PATH, buf ); GetTempFileNameW( buf, L"gdb", 0, tmp ); - if ((f = _wfopen( tmp, L"w+" )) == NULL) return FALSE; + if ((f = _wfopen( tmp, L"w+" )) == NULL) return NULL; unix_tmp = wine_get_unix_file_name( tmp ); fprintf(f, "target remote localhost:%d\n", ntohs(port)); fprintf(f, "set prompt Wine-gdb>\ \n"); @@ -2428,12 +2434,7 @@ static BOOL gdb_exec(unsigned port, unsigned flags) argv[3] = "-x"; argv[4] = unix_tmp; argv[5] = NULL; - if (flags & FLAG_WITH_XTERM) - __wine_unix_spawnvp( (char **)argv, FALSE ); - else - __wine_unix_spawnvp( (char **)argv + 2, FALSE ); - HeapFree( GetProcessHeap(), 0, unix_tmp ); - return TRUE; + return CreateThread( NULL, 0, gdb_ctrl_thread, (flags & FLAG_WITH_XTERM) ? argv : argv + 2, 0, NULL ); }
static BOOL gdb_startup(struct gdb_context* gdbctx, unsigned flags, unsigned port) @@ -2473,7 +2474,7 @@ static BOOL gdb_startup(struct gdb_context* gdbctx, unsigned flags, unsigned por if (flags & FLAG_NO_START) fprintf(stderr, "target remote localhost:%d\n", ntohs(s_addrs.sin_port)); else - gdb_exec(s_addrs.sin_port, flags); + gdbctx->gdb_ctrl_thread = gdb_exec(s_addrs.sin_port, flags);
/* step 4: wait for gdb to connect actually */ FD_ZERO( &read_fds ); @@ -2505,6 +2506,7 @@ static BOOL gdb_init_context(struct gdb_context* gdbctx, unsigned flags, unsigne { int i;
+ gdbctx->gdb_ctrl_thread = NULL; gdbctx->sock = INVALID_SOCKET; gdbctx->in_buf = NULL; gdbctx->in_buf_alloc = 0; @@ -2569,12 +2571,13 @@ static int gdb_remote(unsigned flags, unsigned port) } if (FD_ISSET( gdbctx.sock, &read_fds )) { - if (fetch_data(&gdbctx) > 0) - { - if (extract_packets(&gdbctx)) break; - } + if (fetch_data(&gdbctx) == 0) /* connection closed */ + break; + extract_packets(&gdbctx); } } + /* connection closed, wait for gdb to terminate */ + WaitForSingleObject(gdbctx.gdb_ctrl_thread, INFINITE); return 0; }