/*============================================================================= CADebugMacros.h $Log: CADebugMacros.h,v $ Revision 1.20.4.1 2005/04/21 21:25:35 dwyatt CA_Tiger branch wasn't laid down in the right place for a few files Revision 1.21 2005/03/15 22:50:28 jcm10 use DebugPrintfLineEnding so that syslog doesn't get filled with empty lines Revision 1.20 2004/10/27 01:28:08 jcm10 add more FailIf macros Revision 1.19 2004/09/09 09:14:26 jcm10 add a ThrowIf for Windows errors Revision 1.18 2004/08/25 02:26:26 jcm10 always flush when using the side file Revision 1.17 2004/08/02 18:45:35 dwyatt add LogWarning Revision 1.16 2004/04/13 21:00:55 jcm10 get rid of ThrowError Revision 1.15 2004/04/12 22:58:29 jcm10 fix the macros that used 4CC's to not generate warnings in release builds Revision 1.14 2004/04/01 20:00:36 jcm10 add Throw and clean up the ThrowIf macros Revision 1.13 2004/02/27 01:45:19 jcm10 add ThrowError() Revision 1.12 2004/01/29 22:50:09 jcm10 have AssertNoError print the error number as a 4 char code Revision 1.11 2003/08/29 04:13:55 jcm10 show the time in milliseconds Revision 1.10 2003/07/04 23:56:26 jcm10 add a few more DebugMessages Revision 1.9 2003/06/06 01:51:32 jcm10 clean up some whitespace Revision 1.8 2002/12/14 23:59:58 jcm10 CADebugger is now C compatible so it can be included in pre-compiled headers Revision 1.7 2002/10/02 21:01:40 jcm10 add ThrowIfNULL Revision 1.6 2002/09/11 19:17:55 jcm10 in ThrowIfError, print the error number as a four char code too Revision 1.5 2002/07/20 01:46:45 jcm10 turn off thread stamping Revision 1.4 2002/07/17 21:53:08 jcm10 make the thread stamping and time stamping work right Revision 1.3 2002/07/03 23:49:55 jcm10 add AssertNoKernelError Revision 1.2 2002/05/02 22:31:57 jcm10 display kernel errors in hex Revision 1.1 2002/03/01 01:52:40 jcm10 moved here from ../Utility Revision 1.1 2002/02/28 23:18:54 jcm10 added the CA prefix to the files for more consistency Revision 0.0 Thu Feb 28 2002 14:46:56 US/Pacific moorf Created $NoKeywords: $ =============================================================================*/ #if !defined(__CADebugMacros_h__) #define __CADebugMacros_h__ //============================================================================= // CADebugMacros //============================================================================= //#define CoreAudio_StopOnFailure 1 //#define CoreAudio_TimeStampMessages 1 //#define CoreAudio_ThreadStampMessages 1 //#define CoreAudio_FlushDebugMessages 1 #define CA4CCToCString(the4CC) { ((char*)&the4CC)[0], ((char*)&the4CC)[1], ((char*)&the4CC)[2], ((char*)&the4CC)[3], 0 } #pragma mark Basic Definitions #if DEBUG || CoreAudio_Debug // can be used to break into debugger immediately, also see CADebugger #define BusError() (*(long *)0 = 0) // basic debugging print routines #if TARGET_OS_MAC && !TARGET_API_MAC_CARBON extern pascal void DebugStr(const unsigned char* debuggerMsg); #define DebugMessage(msg) DebugStr("\p"msg) #define DebugMessageN1(msg, N1) #define DebugMessageN2(msg, N1, N2) #define DebugMessageN3(msg, N1, N2, N3) #else #include "CADebugPrintf.h" #if (CoreAudio_FlushDebugMessages && !CoreAudio_UseSysLog) || defined(CoreAudio_UseSideFile) #define FlushRtn ;fflush(DebugPrintfFile) #else #define FlushRtn #endif #if CoreAudio_ThreadStampMessages #include #include "CAHostTimeBase.h" #define DebugMessage(msg) DebugPrintfRtn(DebugPrintfFile, "%p %.4f: %s"DebugPrintfLineEnding, pthread_self(), ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), msg) FlushRtn #define DebugMessageN1(msg, N1) DebugPrintfRtn(DebugPrintfFile, "%p %.4f: "msg"\n", pthread_self(), ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1) FlushRtn #define DebugMessageN2(msg, N1, N2) DebugPrintfRtn(DebugPrintfFile, "%p %.4f: "msg"\n", pthread_self(), ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2) FlushRtn #define DebugMessageN3(msg, N1, N2, N3) DebugPrintfRtn(DebugPrintfFile, "%p %.4f: "msg"\n", pthread_self(), ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2, N3) FlushRtn #define DebugMessageN4(msg, N1, N2, N3, N4) DebugPrintfRtn(DebugPrintfFile, "%p %.4f: "msg"\n", pthread_self(), ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2, N3, N4) FlushRtn #define DebugMessageN5(msg, N1, N2, N3, N4, N5) DebugPrintfRtn(DebugPrintfFile, "%p %.4f: "msg"\n", pthread_self(), ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2, N3, N4, N5) FlushRtn #define DebugMessageN6(msg, N1, N2, N3, N4, N5, N6) DebugPrintfRtn(DebugPrintfFile, "%p %.4f: "msg"\n", pthread_self(), ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2, N3, N4, N5, N6) FlushRtn #define DebugMessageN7(msg, N1, N2, N3, N4, N5, N6, N7) DebugPrintfRtn(DebugPrintfFile, "%p %.4f: "msg"\n", pthread_self(), ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2, N3, N4, N5, N6, N7) FlushRtn #define DebugMessageN8(msg, N1, N2, N3, N4, N5, N6, N7, N8) DebugPrintfRtn(DebugPrintfFile, "%p %.4f: "msg"\n", pthread_self(), ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2, N3, N4, N5, N6, N7, N8) FlushRtn #define DebugMessageN9(msg, N1, N2, N3, N4, N5, N6, N7, N8, N9) DebugPrintfRtn(DebugPrintfFile, "%p %.4f: "msg"\n", pthread_self(), ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2, N3, N4, N5, N6, N7, N8, N9) FlushRtn #elif CoreAudio_TimeStampMessages #include "CAHostTimeBase.h" #define DebugMessage(msg) DebugPrintfRtn(DebugPrintfFile, "%.4f: %s"DebugPrintfLineEnding, pthread_self(), ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), msg) FlushRtn #define DebugMessageN1(msg, N1) DebugPrintfRtn(DebugPrintfFile, "%.4f: "msg DebugPrintfLineEnding, ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1) FlushRtn #define DebugMessageN2(msg, N1, N2) DebugPrintfRtn(DebugPrintfFile, "%.4f: "msg DebugPrintfLineEnding, ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2) FlushRtn #define DebugMessageN3(msg, N1, N2, N3) DebugPrintfRtn(DebugPrintfFile, "%.4f: "msg DebugPrintfLineEnding, ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2, N3) FlushRtn #define DebugMessageN4(msg, N1, N2, N3, N4) DebugPrintfRtn(DebugPrintfFile, "%.4f: "msg DebugPrintfLineEnding, ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2, N3, N4) FlushRtn #define DebugMessageN5(msg, N1, N2, N3, N4, N5) DebugPrintfRtn(DebugPrintfFile, "%.4f: "msg DebugPrintfLineEnding, ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2, N3, N4, N5) FlushRtn #define DebugMessageN6(msg, N1, N2, N3, N4, N5, N6) DebugPrintfRtn(DebugPrintfFile, "%.4f: "msg DebugPrintfLineEnding, ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2, N3, N4, N5, N6) FlushRtn #define DebugMessageN7(msg, N1, N2, N3, N4, N5, N6, N7) DebugPrintfRtn(DebugPrintfFile, "%.4f: "msg DebugPrintfLineEnding, ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2, N3, N4, N5, N6, N7) FlushRtn #define DebugMessageN8(msg, N1, N2, N3, N4, N5, N6, N7, N8) DebugPrintfRtn(DebugPrintfFile, "%.4f: "msg DebugPrintfLineEnding, ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2, N3, N4, N5, N6, N7, N8) FlushRtn #define DebugMessageN9(msg, N1, N2, N3, N4, N5, N6, N7, N8, N9) DebugPrintfRtn(DebugPrintfFile, "%.4f: "msg DebugPrintfLineEnding, ((Float64)(CAHostTimeBase::GetCurrentTimeInNanos()) / 1000000.0), N1, N2, N3, N4, N5, N6, N7, N8, N9) FlushRtn #else #define DebugMessage(msg) DebugPrintfRtn(DebugPrintfFile, "%s"DebugPrintfLineEnding, msg) FlushRtn #define DebugMessageN1(msg, N1) DebugPrintfRtn(DebugPrintfFile, msg DebugPrintfLineEnding, N1) FlushRtn #define DebugMessageN2(msg, N1, N2) DebugPrintfRtn(DebugPrintfFile, msg DebugPrintfLineEnding, N1, N2) FlushRtn #define DebugMessageN3(msg, N1, N2, N3) DebugPrintfRtn(DebugPrintfFile, msg DebugPrintfLineEnding, N1, N2, N3) FlushRtn #define DebugMessageN4(msg, N1, N2, N3, N4) DebugPrintfRtn(DebugPrintfFile, msg DebugPrintfLineEnding, N1, N2, N3, N4) FlushRtn #define DebugMessageN5(msg, N1, N2, N3, N4, N5) DebugPrintfRtn(DebugPrintfFile, msg DebugPrintfLineEnding, N1, N2, N3, N4, N5) FlushRtn #define DebugMessageN6(msg, N1, N2, N3, N4, N5, N6) DebugPrintfRtn(DebugPrintfFile, msg DebugPrintfLineEnding, N1, N2, N3, N4, N5, N6) FlushRtn #define DebugMessageN7(msg, N1, N2, N3, N4, N5, N6, N7) DebugPrintfRtn(DebugPrintfFile, msg DebugPrintfLineEnding, N1, N2, N3, N4, N5, N6, N7) FlushRtn #define DebugMessageN8(msg, N1, N2, N3, N4, N5, N6, N7, N8) DebugPrintfRtn(DebugPrintfFile, msg DebugPrintfLineEnding, N1, N2, N3, N4, N5, N6, N7, N8) FlushRtn #define DebugMessageN9(msg, N1, N2, N3, N4, N5, N6, N7, N8, N9) DebugPrintfRtn(DebugPrintfFile, msg DebugPrintfLineEnding, N1, N2, N3, N4, N5, N6, N7, N8, N9) FlushRtn #endif #endif void DebugPrint(const char *fmt, ...); // can be used like printf #define DEBUGPRINT(msg) DebugPrint msg // have to double-parenthesize arglist (see Debugging.h) #if VERBOSE #define vprint(msg) DEBUGPRINT(msg) #else #define vprint(msg) #endif #if CoreAudio_StopOnFailure #include "CADebugger.h" #define STOP CADebuggerStop() #else #define STOP #endif #else #define DebugMessage(msg) #define DebugMessageN1(msg, N1) #define DebugMessageN2(msg, N1, N2) #define DebugMessageN3(msg, N1, N2, N3) #define DebugMessageN4(msg, N1, N2, N3, N4) #define DebugMessageN5(msg, N1, N2, N3, N4, N5) #define DebugMessageN6(msg, N1, N2, N3, N4, N5, N6) #define DebugMessageN7(msg, N1, N2, N3, N4, N5, N6, N7) #define DebugMessageN8(msg, N1, N2, N3, N4, N5, N6, N7, N8) #define DebugMessageN9(msg, N1, N2, N3, N4, N5, N6, N7, N8, N9) #define DEBUGPRINT(msg) #define vprint(msg) #define STOP #endif void LogError(const char *fmt, ...); // writes to syslog (and stderr if debugging) void LogWarning(const char *fmt, ...); // writes to syslog (and stderr if debugging) #if DEBUG || CoreAudio_Debug #pragma mark Debug Macros #define Assert(inCondition, inMessage) \ if(!(inCondition)) \ { \ DebugMessage(inMessage); \ STOP; \ } #define AssertNoError(inError, inMessage) \ { \ SInt32 __Err = (inError); \ if(__Err != 0) \ { \ char __4CC[5] = CA4CCToCString(__Err); \ DebugMessageN2(inMessage ", Error: %ld (%s)", __Err, __4CC); \ STOP; \ } \ } #define AssertNoKernelError(inError, inMessage) \ { \ unsigned int __Err = (unsigned int)(inError); \ if(__Err != 0) \ { \ DebugMessageN1(inMessage ", Error: 0x%X", __Err); \ STOP; \ } \ } #define FailIf(inCondition, inHandler, inMessage) \ if(inCondition) \ { \ DebugMessage(inMessage); \ STOP; \ goto inHandler; \ } #define FailWithAction(inCondition, inAction, inHandler, inMessage) \ if(inCondition) \ { \ DebugMessage(inMessage); \ STOP; \ { inAction; } \ goto inHandler; \ } #define FailIfNULL(inPointer, inAction, inHandler, inMessage) \ if((inPointer) == NULL) \ { \ DebugMessage(inMessage); \ STOP; \ { inAction; } \ goto inHandler; \ } #define FailIfKernelError(inKernelError, inException, inMessage) \ { \ kern_return_t __Err = (inKernelError); \ if(__Err != 0) \ { \ DebugMessageN1(inMessage ", Error: 0x%X", __Err); \ STOP; \ { inAction; } \ goto inHandler; \ } \ } #define FailIfError(inError, inException, inMessage) \ { \ SInt32 __Err = (inError); \ if(__Err != 0) \ { \ char __4CC[5] = CA4CCToCString(__Err); \ DebugMessageN2(inMessage ", Error: %ld (%s)", __Err, __4CC); \ STOP; \ { inAction; } \ goto inHandler; \ } \ } #if defined(__cplusplus) #define Throw(inException) STOP; throw (inException) #define ThrowIf(inCondition, inException, inMessage) \ if(inCondition) \ { \ DebugMessage(inMessage); \ Throw(inException); \ } #define ThrowIfNULL(inPointer, inException, inMessage) \ if((inPointer) == NULL) \ { \ DebugMessage(inMessage); \ Throw(inException); \ } #define ThrowIfKernelError(inKernelError, inException, inMessage) \ { \ kern_return_t __Err = (inKernelError); \ if(__Err != 0) \ { \ DebugMessageN1(inMessage ", Error: 0x%X", __Err); \ Throw(inException); \ } \ } #define ThrowIfError(inError, inException, inMessage) \ { \ SInt32 __Err = (inError); \ if(__Err != 0) \ { \ char __4CC[5] = CA4CCToCString(__Err); \ DebugMessageN2(inMessage ", Error: %ld (%s)", __Err, __4CC); \ Throw(inException); \ } \ } #if TARGET_OS_WIN32 #define ThrowIfWinError(inError, inException, inMessage) \ { \ HRESULT __Err = (inError); \ if(FAILED(__Err)) \ { \ DebugMessageN1(inMessage ", Error: 0x%X", __Err); \ Throw(inException); \ } \ } #endif #define SubclassResponsibility(inMethodName, inException) \ { \ DebugMessage(inMethodName": Subclasses must implement this method"); \ Throw(inException); \ } #endif // defined(__cplusplus) #else #pragma mark Release Macros #define Assert(inCondition, inMessage) \ if(!(inCondition)) \ { \ STOP; \ } #define AssertNoError(inError, inMessage) \ { \ SInt32 __Err = (inError); \ if(__Err != 0) \ { \ STOP; \ } \ } #define AssertNoKernelError(inError, inMessage) \ { \ unsigned int __Err = (unsigned int)(inError); \ if(__Err != 0) \ { \ STOP; \ } \ } #define FailIf(inCondition, inHandler, inMessage) \ if(inCondition) \ { \ STOP; \ goto inHandler; \ } #define FailWithAction(inCondition, inAction, inHandler, inMessage) \ if(inCondition) \ { \ STOP; \ { inAction; } \ goto inHandler; \ } #define FailIfNULL(inPointer, inAction, inHandler, inMessage) \ if((inPointer) == NULL) \ { \ STOP; \ { inAction; } \ goto inHandler; \ } #define FailIfKernelError(inKernelError, inException, inMessage) \ if((inKernelError) != 0) \ { \ STOP; \ { inAction; } \ goto inHandler; \ } #define FailIfError(inError, inException, inMessage) \ if((inError) != 0) \ { \ STOP; \ { inAction; } \ goto inHandler; \ } #if defined(__cplusplus) #define Throw(inException) STOP; throw (inException) #define ThrowIf(inCondition, inException, inMessage) \ if(inCondition) \ { \ Throw(inException); \ } #define ThrowIfNULL(inPointer, inException, inMessage) \ if((inPointer) == NULL) \ { \ Throw(inException); \ } #define ThrowIfKernelError(inKernelError, inException, inMessage) \ { \ kern_return_t __Err = (inKernelError); \ if(__Err != 0) \ { \ Throw(inException); \ } \ } #define ThrowIfError(inError, inException, inMessage) \ { \ SInt32 __Err = (inError); \ if(__Err != 0) \ { \ Throw(inException); \ } \ } #if TARGET_OS_WIN32 #define ThrowIfWinError(inError, inException, inMessage) \ { \ HRESULT __Err = (inError); \ if(FAILED(__Err)) \ { \ Throw(inException); \ } \ } #endif #define SubclassResponsibility(inMethodName, inException) \ { \ Throw(inException); \ } #endif // defined(__cplusplus) #endif // DEBUG || CoreAudio_Debug #endif