From aef9e00016be696b2b1b06f8f7068dc828b36623 Mon Sep 17 00:00:00 2001 From: Steve Checkoway Date: Fri, 16 Jun 2006 07:18:39 +0000 Subject: [PATCH] Implement IsDebuggerPresent() and DebugBreak() in OS X. This uses an unstable api so it will only be in debug builds. --- stepmania/src/archutils/Darwin/Crash.cpp | 37 ++++++++++++++++++++++++ stepmania/src/archutils/Darwin/Crash.h | 2 ++ stepmania/src/global.cpp | 6 +++- 3 files changed, 44 insertions(+), 1 deletion(-) diff --git a/stepmania/src/archutils/Darwin/Crash.cpp b/stepmania/src/archutils/Darwin/Crash.cpp index 53f0c8134e..df087d8d69 100644 --- a/stepmania/src/archutils/Darwin/Crash.cpp +++ b/stepmania/src/archutils/Darwin/Crash.cpp @@ -2,6 +2,9 @@ #include "Crash.h" #include "ProductInfo.h" #include +#include +#include +#include RString CrashHandler::GetLogsDirectory() { @@ -70,6 +73,40 @@ void CrashHandler::InformUserOfCrash( const RString& sPath ) CFRelease( sAlternate ); } +/* IMPORTANT: Because the definition of the kinfo_proc structure (in ) + * is conditionalized by __APPLE_API_UNSTABLE, you should restrict use of the [below] + * code to the debug build of your program. + * http://developer.apple.com/qa/qa2004/qa1361.html */ +bool CrashHandler::IsDebuggerPresent() +{ +#ifdef DEBUG + int ret; + int mib[] = { CTL_KERN, KERN_PROC, KERN_PROC_PID, getpid() }; + struct kinfo_proc info; + size_t size; + + // Initialize the flags so that, if sysctl fails for some bizarre + // reason, we get a predictable result. + + info.kp_proc.p_flag = 0; + + // Call sysctl. + size = sizeof(info); + ret = sysctl(mib, sizeof(mib) / sizeof(*mib), &info, &size, NULL, 0); + + // We're being debugged if the P_TRACED flag is set. + + return ret == 0 && (info.kp_proc.p_flag & P_TRACED) != 0; +#else + return false; +#endif +} + +void CrashHandler::DebugBreak() +{ + DebugStr( "\pDebugBreak()" ); +} + /* * (c) 2003-2006 Steve Checkoway * All rights reserved. diff --git a/stepmania/src/archutils/Darwin/Crash.h b/stepmania/src/archutils/Darwin/Crash.h index f0728948d9..8dcd37f66c 100644 --- a/stepmania/src/archutils/Darwin/Crash.h +++ b/stepmania/src/archutils/Darwin/Crash.h @@ -5,6 +5,8 @@ namespace CrashHandler { RString GetLogsDirectory(); void InformUserOfCrash( const RString& sPath ); + bool IsDebuggerPresent(); + void DebugBreak(); } #endif /* DARWIN_CRASH_H */ diff --git a/stepmania/src/global.cpp b/stepmania/src/global.cpp index be44bc4ce7..a6bbe1d8ed 100644 --- a/stepmania/src/global.cpp +++ b/stepmania/src/global.cpp @@ -6,6 +6,10 @@ # include "windows.h" # include "archutils/Win32/Crash.h" # endif +#elif defined(MACOSX) +# include "archutils/Darwin/Crash.h" +using CrashHandler::IsDebuggerPresent; +using CrashHandler::DebugBreak; #elif defined(_XBOX) #else # include @@ -17,7 +21,7 @@ void NORETURN sm_crash( const char *reason ) { -#if defined(_WINDOWS) && defined(CRASH_HANDLER) +#if ( defined(_WINDOWS) && defined(CRASH_HANDLER) ) || defined(MACOSX) /* If we're being debugged, throw a debug break so it'll suspend the process. */ if( IsDebuggerPresent() ) {