Setup signal handling and exceptions only after REQ_INIT_PROCESS_DONE
has been sent, to avoid deadlocking the debugger.
This commit is contained in:
parent
9926d33450
commit
42cc2bdf46
|
@ -734,8 +734,6 @@ BOOL SIGNAL_Init(void)
|
|||
}
|
||||
#endif /* HAVE_SIGALTSTACK */
|
||||
|
||||
/* ignore SIGPIPE so that WINSOCK can get a EPIPE error instead */
|
||||
signal( SIGPIPE, SIG_IGN );
|
||||
/* automatic child reaping to avoid zombies */
|
||||
signal( SIGCHLD, SIG_IGN );
|
||||
|
||||
|
|
|
@ -11,6 +11,7 @@
|
|||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <pwd.h>
|
||||
#include <signal.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <sys/types.h>
|
||||
|
@ -411,16 +412,19 @@ static int server_connect( const char *oldcwd, const char *serverdir )
|
|||
fatal_error( "'%s/%s' is not owned by you\n", serverdir, SOCKETNAME );
|
||||
|
||||
/* try to connect to it */
|
||||
if ((s = socket( AF_UNIX, SOCK_STREAM, 0 )) == -1) fatal_perror( "socket" );
|
||||
addr.sun_family = AF_UNIX;
|
||||
strcpy( addr.sun_path, SOCKETNAME );
|
||||
slen = sizeof(addr) - sizeof(addr.sun_path) + strlen(addr.sun_path) + 1;
|
||||
#ifdef HAVE_SOCKADDR_SUN_LEN
|
||||
addr.sun_len = slen;
|
||||
#endif
|
||||
if ((s = socket( AF_UNIX, SOCK_STREAM, 0 )) == -1) fatal_perror( "socket" );
|
||||
if (connect( s, (struct sockaddr *)&addr, slen ) == -1)
|
||||
{
|
||||
usleep( 50000 ); /* in case the server was starting right now */
|
||||
close( s );
|
||||
/* wait a bit and retry with a new socket */
|
||||
usleep( 50000 );
|
||||
if ((s = socket( AF_UNIX, SOCK_STREAM, 0 )) == -1) fatal_perror( "socket" );
|
||||
if (connect( s, (struct sockaddr *)&addr, slen ) == -1)
|
||||
fatal_error( "'%s/%s' exists,\n"
|
||||
" but I cannot connect to it; maybe the server has crashed?\n"
|
||||
|
@ -440,18 +444,10 @@ static int server_connect( const char *oldcwd, const char *serverdir )
|
|||
int CLIENT_InitServer(void)
|
||||
{
|
||||
int fd, size;
|
||||
const char *env_fd;
|
||||
char hostname[64];
|
||||
char *oldcwd, *serverdir;
|
||||
const char *configdir;
|
||||
|
||||
/* first check if we inherited the socket fd */
|
||||
if ((env_fd = getenv( "__WINE_FD" )) && isdigit(env_fd[0]))
|
||||
{
|
||||
fd = atoi( env_fd );
|
||||
if (fcntl( fd, F_SETFD, 1 ) != -1) return fd; /* set close on exec flag */
|
||||
}
|
||||
|
||||
/* retrieve the current directory */
|
||||
for (size = 512; ; size *= 2)
|
||||
{
|
||||
|
@ -497,6 +493,9 @@ int CLIENT_InitThread(void)
|
|||
TEB *teb = NtCurrentTeb();
|
||||
int fd;
|
||||
|
||||
/* ignore SIGPIPE so that we get a EPIPE error instead */
|
||||
signal( SIGPIPE, SIG_IGN );
|
||||
|
||||
if (wait_reply_fd( &fd ) || (fd == -1))
|
||||
server_protocol_error( "no fd passed on first request\n" );
|
||||
if ((teb->buffer_size = lseek( fd, 0, SEEK_END )) == -1) server_perror( "lseek" );
|
||||
|
|
|
@ -207,9 +207,6 @@ BOOL PROCESS_Init(void)
|
|||
initial_envdb.hStdout = initial_startup.hStdOutput = req->hstdout;
|
||||
initial_envdb.hStderr = initial_startup.hStdError = req->hstderr;
|
||||
|
||||
/* Initialize signal handling */
|
||||
if (!SIGNAL_Init()) return FALSE;
|
||||
|
||||
/* Remember TEB selector of initial process for emergency use */
|
||||
SYSLEVEL_EmergencyTeb = NtCurrentTeb()->teb_sel;
|
||||
|
||||
|
@ -318,74 +315,70 @@ static inline char *build_command_line( char **argv )
|
|||
*/
|
||||
static void start_process(void)
|
||||
{
|
||||
__TRY
|
||||
{
|
||||
struct init_process_done_request *req = get_req_buffer();
|
||||
int debugged, console_app;
|
||||
HMODULE16 hModule16;
|
||||
UINT cmdShow = SW_SHOWNORMAL;
|
||||
LPTHREAD_START_ROUTINE entry;
|
||||
PDB *pdb = PROCESS_Current();
|
||||
HMODULE module = pdb->exe_modref->module;
|
||||
struct init_process_done_request *req = get_req_buffer();
|
||||
int debugged, console_app;
|
||||
HMODULE16 hModule16;
|
||||
UINT cmdShow = SW_SHOWNORMAL;
|
||||
LPTHREAD_START_ROUTINE entry;
|
||||
PDB *pdb = PROCESS_Current();
|
||||
HMODULE module = pdb->exe_modref->module;
|
||||
|
||||
/* Increment EXE refcount */
|
||||
pdb->exe_modref->refCount++;
|
||||
/* Increment EXE refcount */
|
||||
pdb->exe_modref->refCount++;
|
||||
|
||||
/* build command line */
|
||||
if (!(pdb->env_db->cmd_line = build_command_line( main_exe_argv ))) goto error;
|
||||
/* build command line */
|
||||
if (!(pdb->env_db->cmd_line = build_command_line( main_exe_argv ))) goto error;
|
||||
|
||||
/* Retrieve entry point address */
|
||||
entry = (LPTHREAD_START_ROUTINE)RVA_PTR( module, OptionalHeader.AddressOfEntryPoint );
|
||||
console_app = (PE_HEADER(module)->OptionalHeader.Subsystem == IMAGE_SUBSYSTEM_WINDOWS_CUI);
|
||||
/* Retrieve entry point address */
|
||||
entry = (LPTHREAD_START_ROUTINE)RVA_PTR( module, OptionalHeader.AddressOfEntryPoint );
|
||||
console_app = (PE_HEADER(module)->OptionalHeader.Subsystem == IMAGE_SUBSYSTEM_WINDOWS_CUI);
|
||||
|
||||
if (console_app) pdb->flags |= PDB32_CONSOLE_PROC;
|
||||
if (console_app) pdb->flags |= PDB32_CONSOLE_PROC;
|
||||
|
||||
/* Signal the parent process to continue */
|
||||
req->module = (void *)module;
|
||||
req->entry = entry;
|
||||
req->gui = !console_app;
|
||||
server_call( REQ_INIT_PROCESS_DONE );
|
||||
debugged = req->debugged;
|
||||
/* Signal the parent process to continue */
|
||||
req->module = (void *)module;
|
||||
req->entry = entry;
|
||||
req->gui = !console_app;
|
||||
server_call( REQ_INIT_PROCESS_DONE );
|
||||
debugged = req->debugged;
|
||||
|
||||
/* Load KERNEL (necessary for TASK_Create) */
|
||||
if (!LoadLibraryA( "KERNEL32" )) goto error;
|
||||
/* Install signal handlers; this cannot be done before, since we cannot
|
||||
* send exceptions to the debugger before the create process event that
|
||||
* is sent by REQ_INIT_PROCESS_DONE */
|
||||
if (!SIGNAL_Init()) goto error;
|
||||
|
||||
/* Create 16-bit dummy module */
|
||||
if ((hModule16 = MODULE_CreateDummyModule( pdb->exe_modref->filename, module )) < 32)
|
||||
ExitProcess( hModule16 );
|
||||
/* Load KERNEL (necessary for TASK_Create) */
|
||||
if (!LoadLibraryA( "KERNEL32" )) goto error;
|
||||
|
||||
if (pdb->env_db->startup_info->dwFlags & STARTF_USESHOWWINDOW)
|
||||
cmdShow = pdb->env_db->startup_info->wShowWindow;
|
||||
if (!TASK_Create( (NE_MODULE *)GlobalLock16( hModule16 ), cmdShow,
|
||||
NtCurrentTeb(), NULL, 0 ))
|
||||
goto error;
|
||||
/* Create 16-bit dummy module */
|
||||
if ((hModule16 = MODULE_CreateDummyModule( pdb->exe_modref->filename, module )) < 32)
|
||||
ExitProcess( hModule16 );
|
||||
|
||||
/* Load the system dlls */
|
||||
if (!load_system_dlls()) goto error;
|
||||
if (pdb->env_db->startup_info->dwFlags & STARTF_USESHOWWINDOW)
|
||||
cmdShow = pdb->env_db->startup_info->wShowWindow;
|
||||
if (!TASK_Create( (NE_MODULE *)GlobalLock16( hModule16 ), cmdShow,
|
||||
NtCurrentTeb(), NULL, 0 ))
|
||||
goto error;
|
||||
|
||||
EnterCriticalSection( &pdb->crit_section );
|
||||
PE_InitTls();
|
||||
MODULE_DllProcessAttach( pdb->exe_modref, (LPVOID)1 );
|
||||
LeaveCriticalSection( &pdb->crit_section );
|
||||
/* Load the system dlls */
|
||||
if (!load_system_dlls()) goto error;
|
||||
|
||||
/* Call UserSignalProc ( USIG_PROCESS_RUNNING ... ) only for non-GUI win32 apps */
|
||||
if (console_app) PROCESS_CallUserSignalProc( USIG_PROCESS_RUNNING, 0 );
|
||||
EnterCriticalSection( &pdb->crit_section );
|
||||
PE_InitTls();
|
||||
MODULE_DllProcessAttach( pdb->exe_modref, (LPVOID)1 );
|
||||
LeaveCriticalSection( &pdb->crit_section );
|
||||
|
||||
TRACE_(relay)( "Starting Win32 process (entryproc=%p)\n", entry );
|
||||
if (debugged) DbgBreakPoint();
|
||||
/* FIXME: should use _PEB as parameter for NT 3.5 programs !
|
||||
* Dunno about other OSs */
|
||||
ExitThread( entry(NULL) );
|
||||
/* Call UserSignalProc ( USIG_PROCESS_RUNNING ... ) only for non-GUI win32 apps */
|
||||
if (console_app) PROCESS_CallUserSignalProc( USIG_PROCESS_RUNNING, 0 );
|
||||
|
||||
error:
|
||||
ExitProcess( GetLastError() );
|
||||
TRACE_(relay)( "Starting Win32 process (entryproc=%p)\n", entry );
|
||||
if (debugged) DbgBreakPoint();
|
||||
/* FIXME: should use _PEB as parameter for NT 3.5 programs !
|
||||
* Dunno about other OSs */
|
||||
ExitThread( entry(NULL) );
|
||||
|
||||
}
|
||||
__EXCEPT(UnhandledExceptionFilter)
|
||||
{
|
||||
TerminateThread( GetCurrentThread(), GetExceptionCode() );
|
||||
}
|
||||
__ENDTRY
|
||||
error:
|
||||
ExitProcess( GetLastError() );
|
||||
}
|
||||
|
||||
|
||||
|
@ -410,8 +403,6 @@ static void PROCESS_Start( HMODULE main_module, LPCSTR filename )
|
|||
PE_HEADER(main_module)->OptionalHeader.SizeOfStackReserve, TRUE ))
|
||||
ExitProcess( GetLastError() );
|
||||
|
||||
SIGNAL_Init(); /* reinitialize signal stack */
|
||||
|
||||
/* switch to the new stack */
|
||||
SYSDEPS_SwitchToThreadStack( start_process );
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue