m3core/src/runtime/common/RTDebugC.c
#ifdef _WIN32
__declspec(dllimport) int __stdcall IsDebuggerPresent(void);
__declspec(dllimport) void __stdcall DebugBreak(void);
int __cdecl RTDebug__IsDebuggerPresent(void)
{
return IsDebuggerPresent();
}
void __cdecl RTDebug__DebugBreak(void)
{
DebugBreak();
}
#else
#include <unistd.h>
#include <signal.h>
#include <stdio.h>
static volatile char inited;
static char is_debugger_present;
static void init(void)
/* todo: test detach/reattach, and maybe make them work */
{
struct sigaction sa;
if (inited)
return;
sigaction(SIGTRAP, 0, &sa);
#ifdef __APPLE__
/* experimentally derived */
if ((sa.sa_mask == 0) != (sa.sa_flags == SA_RESTART))
printf("warning 1 in RTDebug.init\n");
is_debugger_present = (sa.sa_mask == 0) && (sa.sa_flags == SA_RESTART);
#else
/* todo? */
#endif
inited = 1;
}
int RTDebug__IsDebuggerPresent(void)
{
init();
return is_debugger_present;
}
void RTDebug__DebugBreak(void)
/* todo: this is so big/slow compared to Win32! */
{
struct sigaction sa;
sigaction(SIGTRAP, 0, &sa);
signal(SIGTRAP, SIG_IGN);
raise(SIGTRAP);
sigaction(SIGTRAP, &sa, 0);
}
#endif
#if 0 /* test code */
int main()
{
printf("IsDebuggerPresent %d\n", RTDebug__IsDebuggerPresent());
RTDebug__DebugBreak();
printf("after debugbreak (make sure it doesn't exit)\n");
return 0;
}
#endif