From: serassio <> Date: Sun, 28 Aug 2005 01:36:36 +0000 (+0000) Subject: Merge of latest Windows specific updates from nt-3_0 branch: X-Git-Tag: SQUID_3_0_PRE4~666 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=0664883967d612edbcbeb8d3cb6e5b7feedcc385;p=thirdparty%2Fsquid.git Merge of latest Windows specific updates from nt-3_0 branch: - Added native Windows Exception handling with signal() emulation --- diff --git a/src/protos.h b/src/protos.h index 5acc82ee2f..561723c476 100644 --- a/src/protos.h +++ b/src/protos.h @@ -1,6 +1,6 @@ /* - * $Id: protos.h,v 1.506 2005/06/09 07:07:30 hno Exp $ + * $Id: protos.h,v 1.507 2005/08/27 19:36:36 serassio Exp $ * * * SQUID Web Proxy Cache http://www.squid-cache.org/ @@ -1005,6 +1005,7 @@ SQUIDCEXTERN void WIN32_RemoveService(void); #ifdef _SQUID_MSWIN_ SQUIDCEXTERN int WIN32_getrusage(int, struct rusage *); +SQUIDCEXTERN void WIN32_ExceptionHandlerInit(void); #endif /* external_acl.c */ diff --git a/src/tools.cc b/src/tools.cc index 3c67084a48..02a330e37e 100644 --- a/src/tools.cc +++ b/src/tools.cc @@ -1,6 +1,6 @@ /* - * $Id: tools.cc,v 1.258 2005/08/14 18:43:41 serassio Exp $ + * $Id: tools.cc,v 1.259 2005/08/27 19:36:36 serassio Exp $ * * DEBUG: section 21 Misc Functions * AUTHOR: Harvest Derived @@ -346,7 +346,7 @@ death(int sig) #endif #endif /* PRINT_STACK_TRACE */ -#if SA_RESETHAND == 0 +#if SA_RESETHAND == 0 && !defined(_SQUID_MSWIN_) signal(SIGSEGV, SIG_DFL); signal(SIGBUS, SIG_DFL); @@ -937,9 +937,45 @@ squid_signal(int sig, SIGHDLR * func, int flags) debug(50, 0) ("sigaction: sig=%d func=%p: %s\n", sig, func, xstrerror()); #else +#ifdef _SQUID_MSWIN_ + /* + On Windows, only SIGINT, SIGILL, SIGFPE, SIGTERM, SIGBREAK, SIGABRT and SIGSEGV signals + are supported, so we must care of don't call signal() for other value. + The SIGILL, SIGSEGV, and SIGTERM signals are not generated under Windows. They are defined + for ANSI compatibility, so both SIGSEGV and SIGBUS are emulated with an Exception Handler. + */ + switch (sig) { + + case SIGINT: + + case SIGILL: + + case SIGFPE: + + case SIGTERM: + + case SIGBREAK: + + case SIGABRT: + break; + + case SIGSEGV: + WIN32_ExceptionHandlerInit(); + break; + + case SIGBUS: + WIN32_ExceptionHandlerInit(); + return; + break; /* Nor reached */ + + default: + return; + break; /* Nor reached */ + } + +#endif - if (signal(sig, func) == SIG_ERR) - debug(50, 0) ("signal: sig=%d func=%p: %s\n", sig, func, xstrerror()); + signal(sig, func); #endif } diff --git a/src/win32.cc b/src/win32.cc index 436f829a59..1f02fab49c 100644 --- a/src/win32.cc +++ b/src/win32.cc @@ -1,6 +1,6 @@ /* - * $Id: win32.cc,v 1.13 2004/12/20 16:30:37 robertc Exp $ + * $Id: win32.cc,v 1.14 2005/08/27 19:36:36 serassio Exp $ * * * * * * * * * Legal stuff * * * * * * * * @@ -39,9 +39,14 @@ #define WIN32_C #include "squid.h" - #include "squid_windows.h" +#ifdef _SQUID_MSWIN_ +#if defined(_MSC_VER) /* Microsoft C Compiler ONLY */ +#include +#endif +#endif + static unsigned int GetOSVersion(); void WIN32_svcstatusupdate(DWORD, DWORD); void WINAPI WIN32_svcHandler(DWORD); @@ -52,7 +57,16 @@ static void WIN32_build_argv (char *); #endif extern "C" void WINAPI SquidMain(DWORD, char **); +#if defined(_SQUID_MSWIN_) +#if defined(_MSC_VER) /* Microsoft C Compiler ONLY */ +void Squid_Win32InvalidParameterHandler(const wchar_t*, const wchar_t*, const wchar_t*, unsigned int, uintptr_t); +#endif +void WIN32_ExceptionHandlerCleanup(void); +static LPTOP_LEVEL_EXCEPTION_FILTER Win32_Old_ExceptionHandler = NULL; +#endif + static int Squid_Aborting = 0; + #if USE_WIN32_SERVICE static SERVICE_STATUS svcStatus; static SERVICE_STATUS_HANDLE svcHandle; @@ -380,6 +394,10 @@ WIN32_Exit() } } +#endif +#ifdef _SQUID_MSWIN_ + WIN32_ExceptionHandlerCleanup(); + #endif _exit(0); @@ -392,6 +410,10 @@ int WIN32_Subsystem_Init() #endif { +#if defined(_MSC_VER) /* Microsoft C Compiler ONLY */ + _invalid_parameter_handler oldHandler, newHandler; +#endif + WIN32_OS_version = GetOSVersion(); if ((WIN32_OS_version == _WIN_OS_UNKNOWN) || (WIN32_OS_version == _WIN_OS_WIN32S)) @@ -400,6 +422,15 @@ WIN32_Subsystem_Init() if (atexit(WIN32_Exit) != 0) return 1; +#if defined(_MSC_VER) /* Microsoft C Compiler ONLY */ + + newHandler = Squid_Win32InvalidParameterHandler; + + oldHandler = _set_invalid_parameter_handler(newHandler); + + _CrtSetReportMode(_CRT_ASSERT, 0); + +#endif #if USE_WIN32_SERVICE if (WIN32_run_mode == _WIN_SQUID_RUN_MODE_SERVICE) @@ -858,4 +889,55 @@ int main(int argc, char **argv) #endif /* USE_WIN32_SERVICE */ +#if defined(_SQUID_MSWIN_) +void Squid_Win32InvalidParameterHandler(const wchar_t* expression, const wchar_t* function, const wchar_t* file, unsigned int line, uintptr_t pReserved) +{ + return; +} + +LONG CALLBACK WIN32_ExceptionHandler(EXCEPTION_POINTERS* ep) +{ + EXCEPTION_RECORD* er; + + er = ep->ExceptionRecord; + + switch (er->ExceptionCode) { + + case EXCEPTION_ACCESS_VIOLATION: + raise(SIGSEGV); + break; + + case EXCEPTION_DATATYPE_MISALIGNMENT: + + case EXCEPTION_ARRAY_BOUNDS_EXCEEDED: + + case EXCEPTION_IN_PAGE_ERROR: + death(SIGBUS); + break; + + default: + break; + } + + return EXCEPTION_CONTINUE_SEARCH; +} + + +void WIN32_ExceptionHandlerInit() +{ +#if !defined(_DEBUG) + + if (Win32_Old_ExceptionHandler == NULL) + Win32_Old_ExceptionHandler = SetUnhandledExceptionFilter(WIN32_ExceptionHandler); + +#endif +} + +void WIN32_ExceptionHandlerCleanup() +{ + if (Win32_Old_ExceptionHandler != NULL) + SetUnhandledExceptionFilter(Win32_Old_ExceptionHandler); +} + +#endif #endif /* WIN32_C */