// debugging support
// -----------------
-#ifdef __WXDEBUG__
// this function is called when an assert failure occurs, the base class
// version does the normal processing (i.e. shows the usual assert failure
// dialog box)
int line,
const wxChar *cond,
const wxChar *msg);
-#endif // __WXDEBUG__
// check that the wxBuildOptions object (constructed in the application
// itself, usually the one from IMPLEMENT_APP() macro) matches the build
// functions abstracting differences between GUI and console modes
// ------------------------------------------------------------------------
-#ifdef __WXDEBUG__
// show the assert dialog with the specified message in GUI or just print
// the string to stderr in console mode
//
//
// return true to suppress subsequent asserts, false to continue as before
virtual bool ShowAssertDialog(const wxString& msg) = 0;
-#endif // __WXDEBUG__
// return true if fprintf(stderr) goes somewhere, false otherwise
virtual bool HasStderr() = 0;
protected:
-#if wxUSE_STACKWALKER && defined( __WXDEBUG__ )
+#if wxUSE_STACKWALKER
// utility function: returns the stack frame as a plain wxString
virtual wxString GetAssertStackTrace();
#endif
#endif // wxUSE_FONTMAP
virtual wxRendererNative *CreateRenderer();
-#ifdef __WXDEBUG__
virtual bool ShowAssertDialog(const wxString& msg);
-#endif // __WXDEBUG__
virtual bool HasStderr();
virtual void ScheduleForDestroy(wxObject *object);
#endif // wxUSE_FONTMAP
virtual wxRendererNative *CreateRenderer();
-#ifdef __WXDEBUG__
virtual bool ShowAssertDialog(const wxString& msg);
-#endif // __WXDEBUG__
virtual bool HasStderr();
virtual void ScheduleForDestroy(wxObject *object);
virtual bool OnInit();
virtual bool OnInitGui();
-#ifdef __WXDEBUG__
- virtual void OnAssert(const wxChar *file, int line, const wxChar *cond, const wxChar *msg);
- bool IsInAssert() const { return m_isInAssert; }
-#endif // __WXDEBUG__
-
// Set true _before_ initializing wx to force embedded mode (no app delegate, etc.)
static bool sm_isEmbedded;
-private:
-#ifdef __WXDEBUG__
- bool m_isInAssert;
-#endif // __WXDEBUG__
};
#endif // _WX_COCOA_APP_H_
void* GetID() const { return m_id; }
operator const void* () const { return m_id; }
-#ifdef __WXDEBUG__
- void Print( const wxString &text ) const;
-#endif
-
private:
void* m_id;
};
#define wxAutoBufferedPaintDCBase wxBufferedPaintDC
#endif
-
-#ifdef __WXDEBUG__
-
class WXDLLIMPEXP_CORE wxAutoBufferedPaintDC : public wxAutoBufferedPaintDCBase
{
public:
wxAutoBufferedPaintDC(wxWindow* win)
: wxAutoBufferedPaintDCBase(win)
{
- TestWinStyle(win);
+ wxASSERT_MSG( win->GetBackgroundStyle() == wxBG_STYLE_CUSTOM,
+ "You need to call SetBackgroundStyle(wxBG_STYLE_CUSTOM) in ctor, "
+ "and also, if needed, paint the background in wxEVT_PAINT handler."
+ );
}
virtual ~wxAutoBufferedPaintDC() { }
private:
-
- void TestWinStyle(wxWindow* win)
- {
- // Help the user to get the double-buffering working properly.
- wxASSERT_MSG( win->GetBackgroundStyle() == wxBG_STYLE_CUSTOM,
- wxT("In constructor, you need to call SetBackgroundStyle(wxBG_STYLE_CUSTOM), ")
- wxT("and also, if needed, paint the background manually in the paint event handler."));
- }
-
wxDECLARE_NO_COPY_CLASS(wxAutoBufferedPaintDC);
};
-#else // !__WXDEBUG__
-
-// In release builds, just use typedef
-typedef wxAutoBufferedPaintDCBase wxAutoBufferedPaintDC;
-
-#endif
// Check if the window is natively double buffered and will return a wxPaintDC
#include "wx/chartype.h" // for __TFILE__ and wxChar
#include "wx/cpp.h" // for __WXFUNCTION__
+class WXDLLIMPEXP_FWD_BASE wxString;
+class WXDLLIMPEXP_FWD_BASE wxCStrData;
+
// ----------------------------------------------------------------------------
// Defines controlling the debugging macros
// ----------------------------------------------------------------------------
+/*
+ wxWidgets can be built with several different levels of debug support
+ specified by the value of wxDEBUG_LEVEL constant:
+
+ 0: No assertion macros at all, this should only be used when optimizing
+ for resource-constrained systems (typically embedded ones).
+ 1: Default level, most of the assertions are enabled.
+ 2: Maximal (at least for now): asserts which are "expensive"
+ (performance-wise) or only make sense for finding errors in wxWidgets
+ itself, as opposed to bugs in applications using it, are also enabled.
+
+ For compatibility reasons, currently wxDEBUG_LEVEL is defined if
+ __WXDEBUG__ is defined but in the near future (2.9.1) the role of the flags
+ will change and wxDEBUG_LEVEL will be the primary value with __WXDEBUG__
+ only used for compatibility.
+ */
+
// if _DEBUG is defined (MS VC++ and others use it in debug builds), define
// __WXDEBUG__ too
#ifdef _DEBUG
#endif // !WXDEBUG
#endif // __WXDEBUG__
+// temporarily define wxDEBUG_LEVEL as function of __WXDEBUG__
+#if !defined(wxDEBUG_LEVEL)
+ #ifdef __WXDEBUG__
+ #define wxDEBUG_LEVEL 1
+ #else
+ #define wxDEBUG_LEVEL 0
+ #endif
+#endif // !defined(wxDEBUG_LEVEL)
+
// ----------------------------------------------------------------------------
-// Debugging macros
-//
-// All debugging macros rely on ASSERT() which in turn calls the user-defined
-// OnAssert() function. To keep things simple, it's called even when the
-// expression is true (i.e. everything is ok) and by default does nothing: just
-// returns the same value back. But if you redefine it to do something more sexy
-// (popping up a message box in your favourite GUI, sending you e-mail or
-// whatever) it will affect all ASSERTs, FAILs and CHECKs in your code.
-//
-// Warning: if you don't like advice on programming style, don't read
-// further! ;-)
-//
-// Extensive use of these macros is recommended! Remember that ASSERTs are
-// disabled in final build (without __WXDEBUG__ defined), so they add strictly
-// nothing to your program's code. On the other hand, CHECK macros do stay
-// even in release builds, but in general are not much of a burden, while
-// a judicious use of them might increase your program's stability.
+// Handling assertion failures
// ----------------------------------------------------------------------------
-// Macros which are completely disabled in 'release' mode
+/*
+ Type for the function called in case of assert failure, see
+ wxSetAssertHandler().
+ */
+typedef void (*wxAssertHandler_t)(const wxString& file,
+ int line,
+ const wxString& func,
+ const wxString& cond,
+ const wxString& msg);
+
+#if wxDEBUG_LEVEL
+
+// the global assert handler function, if it is NULL asserts don't check their
+// conditions
+extern WXDLLIMPEXP_DATA_BASE(wxAssertHandler_t) wxTheAssertHandler;
+
+/*
+ Sets the function to be called in case of assertion failure.
+
+ The default assert handler forwards to wxApp::OnAssertFailure() whose
+ default behaviour is, in turn, to show the standard assertion failure
+ dialog if a wxApp object exists or shows the same dialog itself directly
+ otherwise.
+
+ While usually it is enough -- and more convenient -- to just override
+ OnAssertFailure(), to handle all assertion failures, including those
+ occurring even before wxApp object creation of after its destruction you
+ need to provide your assertion handler function.
+
+ This function also provides a simple way to disable all asserts: simply
+ pass NULL pointer to it. Doing this will result in not even evaluating
+ assert conditions at all, avoiding almost all run-time cost of asserts.
+
+ Notice that this function is not MT-safe, so you should call it before
+ starting any other threads.
+
+ The return value of this function is the previous assertion handler. It can
+ be called after any pre-processing by your handler and can also be restored
+ later if you uninstall your handler.
+ */
+inline wxAssertHandler_t wxSetAssertHandler(wxAssertHandler_t handler)
+{
+ const wxAssertHandler_t old = wxTheAssertHandler;
+ wxTheAssertHandler = handler;
+ return old;
+}
+
+#else // !wxDEBUG_LEVEL
+
+// provide empty subs in case assertions are completely disabled
//
-// NB: these functions are implemented in src/common/appcmn.cpp
-#if defined(__WXDEBUG__)
- /*
- This function is called whenever one of debugging macros fails (i.e.
- condition is false in an assertion). To customize its behaviour, override
- wxApp::OnAssertFailure().
-
- Parameters:
- szFile and nLine - file name and line number of the ASSERT
- szFunc - function name of the ASSERT, may be NULL (NB: ASCII)
- szCond - text form of the condition which failed
- szMsg - optional message explaining the reason
- */
-
- /* this version is for compatibility with wx 2.8 Unicode build only: */
- extern void WXDLLIMPEXP_BASE wxOnAssert(const wxChar *szFile,
- int nLine,
- const char *szFunc,
- const wxChar *szCond,
- const wxChar *szMsg = NULL);
+// NB: can't use WXUNUSED() here as we're included from wx/defs.h before it is
+// defined
+inline wxAssertHandler_t wxSetAssertHandler(wxAssertHandler_t /* handler */)
+{
+ return NULL;
+}
+
+#endif // wxDEBUG_LEVEL/!wxDEBUG_LEVEL
+
+// simply a synonym for wxSetAssertHandler(NULL)
+inline void wxDisableAsserts() { wxSetAssertHandler(NULL); }
+
+#if wxDEBUG_LEVEL
+
+/*
+ wxOnAssert() is used by the debugging macros defined below. Different
+ overloads are needed because these macros can be used with or without _T().
+
+ All of them are implemented in src/common/appcmn.cpp and unconditionally
+ call wxTheAssertHandler so the caller must check that it is non-NULL
+ (assert macros do it).
+ */
#if wxUSE_UNICODE
- /* char versions are used by debugging macros; we have to provide
- wxChar* szMsg version because it's common to use _T() in the macros
- and finally, we can't use const wx(char)* szMsg = NULL, because that
- would be ambiguous: */
- extern void WXDLLIMPEXP_BASE wxOnAssert(const char *szFile,
- int nLine,
- const char *szFunc,
- const char *szCond);
-
- extern void WXDLLIMPEXP_BASE wxOnAssert(const char *szFile,
- int nLine,
- const char *szFunc,
- const char *szCond,
- const char *szMsg);
-
- extern void WXDLLIMPEXP_BASE wxOnAssert(const char *szFile,
- int nLine,
- const char *szFunc,
- const char *szCond,
- const wxChar *szMsg);
+
+// these overloads are the ones typically used by debugging macros: we have to
+// provide wxChar* msg version because it's common to use _T() in the macros
+// and finally, we can't use const wx(char)* msg = NULL, because that would
+// be ambiguous
+//
+// also notice that these functions can't be inline as wxString is not defined
+// yet (and can't be as wxString code itself may use assertions)
+extern void WXDLLIMPEXP_BASE wxOnAssert(const char *file,
+ int line,
+ const char *func,
+ const char *cond);
+
+extern void WXDLLIMPEXP_BASE wxOnAssert(const char *file,
+ int line,
+ const char *func,
+ const char *cond,
+ const char *msg);
+
+extern void WXDLLIMPEXP_BASE wxOnAssert(const char *file,
+ int line,
+ const char *func,
+ const char *cond,
+ const wxChar *msg);
#endif /* wxUSE_UNICODE */
- class WXDLLIMPEXP_FWD_BASE wxString;
- class WXDLLIMPEXP_FWD_BASE wxCStrData;
-
- /* these two work when szMsg passed to debug macro is a string,
- we also have to provide wxCStrData overload to resolve ambiguity
- which would otherwise arise from wxASSERT( s.c_str() ): */
- extern void WXDLLIMPEXP_BASE wxOnAssert(const wxString& szFile,
- int nLine,
- const wxString& szFunc,
- const wxString& szCond,
- const wxString& szMsg);
-
- extern void WXDLLIMPEXP_BASE wxOnAssert(const wxString& szFile,
- int nLine,
- const wxString& szFunc,
- const wxString& szCond);
-
- extern void WXDLLIMPEXP_BASE wxOnAssert(const char *szFile,
- int nLine,
- const char *szFunc,
- const char *szCond,
- const wxCStrData& msg);
-
- extern void WXDLLIMPEXP_BASE wxOnAssert(const char *szFile,
- int nLine,
- const char *szFunc,
- const char *szCond,
- const wxString& szMsg);
-
- // call this function to break into the debugger unconditionally (assuming
- // the program is running under debugger, of course)
- extern void WXDLLIMPEXP_BASE wxTrap();
-
- // generic assert macro
- #define wxASSERT(cond) wxASSERT_MSG(cond, (const char*)NULL)
-
-
- // assert with additional message explaining its cause
-
- // Note: some compilers will give a warning (such as
- // "possible unwanted ;") when using a ";" instead of the "{}".
- #define wxASSERT_MSG(cond, msg) \
- if ( cond ) \
- {} \
- else \
- wxOnAssert(__FILE__, __LINE__, __WXFUNCTION__, #cond, msg)
-
- // special form of assert: always triggers it (in debug mode)
- #define wxFAIL wxFAIL_MSG((const char*)NULL)
-
- // FAIL with some message
- #define wxFAIL_MSG(msg) wxFAIL_COND_MSG("wxAssertFailure", msg)
-
- // FAIL with some message and a condition
- #define wxFAIL_COND_MSG(cond, msg) \
- wxOnAssert(__FILE__, __LINE__, __WXFUNCTION__, cond, msg)
-
- // An assert helper used to avoid warning when testing constant expressions,
- // i.e. wxASSERT( sizeof(int) == 4 ) can generate a compiler warning about
- // expression being always true, but not using
- // wxASSERT( wxAssertIsEqual(sizeof(int), 4) )
- //
- // NB: this is made obsolete by wxCOMPILE_TIME_ASSERT() and should no
- // longer be used.
- extern bool WXDLLIMPEXP_BASE wxAssertIsEqual(int x, int y);
-#else
- #define wxTrap()
+// this version is for compatibility with wx 2.8 Unicode build only, we don't
+// use it ourselves any more except in ANSI-only build in which case it is all
+// we need
+extern void WXDLLIMPEXP_BASE wxOnAssert(const wxChar *file,
+ int line,
+ const char *func,
+ const wxChar *cond,
+ const wxChar *msg = NULL);
+
+// these overloads work when msg passed to debug macro is a string and we
+// also have to provide wxCStrData overload to resolve ambiguity which would
+// otherwise arise from wxASSERT( s.c_str() )
+extern void WXDLLIMPEXP_BASE wxOnAssert(const wxString& file,
+ int line,
+ const wxString& func,
+ const wxString& cond,
+ const wxString& msg);
+
+extern void WXDLLIMPEXP_BASE wxOnAssert(const wxString& file,
+ int line,
+ const wxString& func,
+ const wxString& cond);
+
+extern void WXDLLIMPEXP_BASE wxOnAssert(const char *file,
+ int line,
+ const char *func,
+ const char *cond,
+ const wxCStrData& msg);
+
+extern void WXDLLIMPEXP_BASE wxOnAssert(const char *file,
+ int line,
+ const char *func,
+ const char *cond,
+ const wxString& msg);
+
+#endif // wxDEBUG_LEVEL
- // nothing to do in release mode (hopefully at this moment there are
- // no more bugs ;-)
- #define wxASSERT(cond)
- #define wxASSERT_MSG(cond, msg)
- #define wxFAIL
- #define wxFAIL_MSG(msg)
- #define wxFAIL_COND_MSG(cond, msg)
-#endif /* __WXDEBUG__ */
-// Use of wxFalse instead of false suppresses compiler warnings about testing
-// constant expression
-extern WXDLLIMPEXP_DATA_BASE(const bool) wxFalse;
+// ----------------------------------------------------------------------------
+// Debugging macros
+// ----------------------------------------------------------------------------
-#define wxAssertFailure wxFalse
+/*
+ Assertion macros: check if the condition is true and call assert handler
+ (which will by default notify the user about failure) if it isn't.
-// NB: the following macros also work in release mode!
+ wxASSERT and wxFAIL macros as well as wxTrap() function do nothing at all
+ if wxDEBUG_LEVEL is 0 however they do check their conditions at default
+ debug level 1, unlike the previous wxWidgets versions.
-/*
- These macros must be used only in invalid situation: for example, an
- invalid parameter (e.g. a NULL pointer) is passed to a function. Instead of
- dereferencing it and causing core dump the function might try using
- CHECK( p != NULL ) or CHECK( p != NULL, return LogError("p is NULL!!") )
-*/
+ wxASSERT_LEVEL_2 is meant to be used for "expensive" asserts which should
+ normally be disabled because they have a big impact on performance and so
+ this macro only does anything if wxDEBUG_LEVEL >= 2.
+ */
+#if wxDEBUG_LEVEL
+ // call this function to break into the debugger unconditionally (assuming
+ // the program is running under debugger, of course)
+ extern void WXDLLIMPEXP_BASE wxTrap();
+
+ // assert checks if the condition is true and calls the assert handler with
+ // the provided message if it isn't
+ //
+ // NB: the macro is defined like this to ensure that nested if/else
+ // statements containing it are compiled in the same way whether it is
+ // defined as empty or not; also notice that we can't use ";" instead
+ // of "{}" as some compilers warn about "possible unwanted ;" then
+ #define wxASSERT_MSG(cond, msg) \
+ if ( !wxTheAssertHandler || (cond) ) \
+ {} \
+ else \
+ wxOnAssert(__FILE__, __LINE__, __WXFUNCTION__, #cond, msg)
+
+ // a version without any additional message, don't use unless condition
+ // itself is fully self-explanatory
+ #define wxASSERT(cond) wxASSERT_MSG(cond, (const char*)NULL)
+
+ // wxFAIL is a special form of assert: it always triggers (and so is
+ // usually used in normally unreachable code)
+ #define wxFAIL_COND_MSG(cond, msg) \
+ wxOnAssert(__FILE__, __LINE__, __WXFUNCTION__, cond, msg)
+ #define wxFAIL_MSG(msg) wxFAIL_COND_MSG("Assert failure", msg)
+ #define wxFAIL wxFAIL_MSG((const char*)NULL)
+#else // !wxDEBUG_LEVEL
+ #define wxTrap()
+
+ #define wxASSERT(cond)
+ #define wxASSERT_MSG(cond, msg)
+ #define wxFAIL
+ #define wxFAIL_MSG(msg)
+ #define wxFAIL_COND_MSG(cond, msg)
+#endif // wxDEBUG_LEVEL
+
+#if wxDEBUG_LEVEL >= 2
+ #define wxASSERT_LEVEL_2_MSG(cond, msg) wxASSERT_MSG(cond, msg)
+ #define wxASSERT_LEVEL_2(cond) wxASSERT(cond)
+#else // wxDEBUG_LEVEL < 2
+ #define wxASSERT_LEVEL_2_MSG
+ #define wxASSERT_LEVEL_2
+#endif
-// check that expression is true, "return" if not (also FAILs in debug mode)
-#define wxCHECK(cond, rc) wxCHECK_MSG(cond, rc, (const char*)NULL)
-// as wxCHECK but with a message explaining why we fail
-#define wxCHECK_MSG(cond, rc, msg) wxCHECK2_MSG(cond, return rc, msg)
+/*
+ wxCHECK macros always check their conditions, setting debug level to 0 only
+ makes them silent in case of failure, otherwise -- including at default
+ debug level 1 -- they call the assert handler if the condition is false
-// check that expression is true, perform op if not
-#define wxCHECK2(cond, op) wxCHECK2_MSG(cond, op, (const char*)NULL)
+ They are supposed to be used only in invalid situation: for example, an
+ invalid parameter (e.g. a NULL pointer) is passed to a function. Instead of
+ dereferencing it and causing core dump the function might use
-// as wxCHECK2 but with a message explaining why we fail
+ wxCHECK_RET( p != NULL, "pointer can't be NULL" )
+*/
+// the generic macro: takes the condition to check, the statement to be execute
+// in case the condition is false and the message to pass to the assert handler
#define wxCHECK2_MSG(cond, op, msg) \
if ( cond ) \
{} \
} \
struct wxDummyCheckStruct /* just to force a semicolon */
+// check which returns with the specified return code if the condition fails
+#define wxCHECK_MSG(cond, rc, msg) wxCHECK2_MSG(cond, return rc, msg)
+
+// check that expression is true, "return" if not (also FAILs in debug mode)
+#define wxCHECK(cond, rc) wxCHECK_MSG(cond, rc, (const char*)NULL)
+
+// check that expression is true, perform op if not
+#define wxCHECK2(cond, op) wxCHECK2_MSG(cond, op, (const char*)NULL)
+
// special form of wxCHECK2: as wxCHECK, but for use in void functions
//
// NB: there is only one form (with msg parameter) and it's intentional:
// to begin with...)
#define wxCHECK_RET(cond, msg) wxCHECK2_MSG(cond, return, msg)
+
// ----------------------------------------------------------------------------
// Compile time asserts
//
// Unlike the normal assert and related macros above which are checked during
-// the program tun-time the macros below will result in a compilation error if
+// the program run-time the macros below will result in a compilation error if
// the condition they check is false. This is usually used to check the
// expressions containing sizeof()s which cannot be tested with the
// preprocessor. If you can use the #if's, do use them as you can give a more
wxCOMPILE_TIME_ASSERT(sizeof(type) * CHAR_BIT >= size, \
wxMAKE_BITSIZE_MSG(type, size))
+
// ----------------------------------------------------------------------------
// other miscellaneous debugger-related functions
// ----------------------------------------------------------------------------
inline bool wxIsDebuggerRunning() { return false; }
#endif // Mac/!Mac
+// An assert helper used to avoid warning when testing constant expressions,
+// i.e. wxASSERT( sizeof(int) == 4 ) can generate a compiler warning about
+// expression being always true, but not using
+// wxASSERT( wxAssertIsEqual(sizeof(int), 4) )
+//
+// NB: this is made obsolete by wxCOMPILE_TIME_ASSERT() and should no
+// longer be used.
+extern bool WXDLLIMPEXP_BASE wxAssertIsEqual(int x, int y);
+
+// Use of wxFalse instead of false suppresses compiler warnings about testing
+// constant expression
+extern WXDLLIMPEXP_DATA_BASE(const bool) wxFalse;
+
+#define wxAssertFailure wxFalse
+
+// This is similar to WXUNUSED() and useful for parameters which are only used
+// in assertions.
+#if wxDEBUG_LEVEL
+ #define WXUNUSED_UNLESS_DEBUG(param) param
+#else
+ #define WXUNUSED_UNLESS_DEBUG(param) WXUNUSED(param)
+#endif
+
+
#endif // _WX_DEBUG_H_
#define WXUNUSED(identifier) identifier
#endif
-/* some arguments are only used in debug mode, but unused in release one */
-#ifdef __WXDEBUG__
- #define WXUNUSED_UNLESS_DEBUG(param) param
-#else
- #define WXUNUSED_UNLESS_DEBUG(param) WXUNUSED(param)
-#endif
-
/* some arguments are not used in unicode mode */
#if wxUSE_UNICODE
#define WXUNUSED_IN_UNICODE(param) WXUNUSED(param)
wxEVT_PAINT_ICON
*/
-#if defined(__WXDEBUG__) && (defined(__WXMSW__) || defined(__WXPM__))
+#if wxDEBUG_LEVEL && (defined(__WXMSW__) || defined(__WXPM__))
+ #define wxHAS_PAINT_DEBUG
+
// see comments in src/msw|os2/dcclient.cpp where g_isPainting is defined
extern WXDLLIMPEXP_CORE int g_isPainting;
#endif // debug
wxPaintEvent(int Id = 0)
: wxEvent(Id, wxEVT_PAINT)
{
-#if defined(__WXDEBUG__) && (defined(__WXMSW__) || defined(__WXPM__))
- // set the internal flag for the duration of processing of WM_PAINT
+#ifdef wxHAS_PAINT_DEBUG
+ // set the internal flag for the duration of redrawing
g_isPainting++;
#endif // debug
}
// default copy ctor and dtor are normally fine, we only need them to keep
// g_isPainting updated in debug build
-#if defined(__WXDEBUG__) && (defined(__WXMSW__) || defined(__WXPM__))
+#ifdef wxHAS_PAINT_DEBUG
wxPaintEvent(const wxPaintEvent& event)
: wxEvent(event)
{
// Clear table
void Clear();
-#if defined(__WXDEBUG__) && wxUSE_MEMORY_TRACING
- // Clear all tables
+#if wxUSE_MEMORY_TRACING
+ // Clear all tables: only used to work around problems in memory tracing
+ // code
static void ClearAll();
-#endif // __WXDEBUG__ && wxUSE_MEMORY_TRACING
+#endif // wxUSE_MEMORY_TRACING
protected:
// Init the hash table with the entries of the static event table.
virtual bool Initialize(int& argc, wxChar **argv);
virtual void CleanUp();
-#ifdef __WXDEBUG__
virtual void OnAssertFailure(const wxChar *file,
int line,
const wxChar *func,
const wxChar *cond,
const wxChar *msg);
-#endif // __WXDEBUG__
// GTK-specific methods
// -------------------
private:
// true if we're inside an assert modal dialog
-#ifdef __WXDEBUG__
bool m_isInAssert;
-#endif // __WXDEBUG__
+
#if wxUSE_THREADS
wxMutex* m_idleMutex;
#endif
static bool InitialzeVisual();
-#ifdef __WXDEBUG__
- virtual void OnAssert(const wxChar *file, int line, const wxChar *cond, const wxChar *msg);
+ virtual void OnAssertFailure(const wxChar *file,
+ int line,
+ const wxChar *func,
+ const wxChar *cond,
+ const wxChar *msg);
bool IsInAssert() const { return m_isInAssert; }
-#endif // __WXDEBUG__
gint m_idleTag;
void RemoveIdleTag();
private:
// true if we're inside an assert modal dialog
-#ifdef __WXDEBUG__
bool m_isInAssert;
-#endif // __WXDEBUG__
DECLARE_DYNAMIC_CLASS(wxApp)
};
void SendEvent();
};
-#ifndef __WXDEBUG__
-inline void wxHyperlinkCtrlBase::CheckParams(const wxString&, const wxString&, long) { }
-#endif
-
// ----------------------------------------------------------------------------
// wxHyperlinkEvent
// ----------------------------------------------------------------------------
// Licence: wxWindows licence
/////////////////////////////////////////////////////////////////////////////
-#ifndef _WX_MEMORYH__
-#define _WX_MEMORYH__
+#ifndef _WX_MEMORY_H_
+#define _WX_MEMORY_H_
#include "wx/defs.h"
#include "wx/string.h"
#include "wx/msgout.h"
-/*
- The macro which will be expanded to include the file and line number
- info, or to be a straight call to the new operator.
-*/
-
-#if (defined(__WXDEBUG__) && wxUSE_MEMORY_TRACING) || wxUSE_DEBUG_CONTEXT
+#if wxUSE_MEMORY_TRACING || wxUSE_DEBUG_CONTEXT
#include <stddef.h>
-#ifdef __WXDEBUG__
-
WXDLLIMPEXP_BASE void * wxDebugAlloc(size_t size, wxChar * fileName, int lineNum, bool isObject, bool isVect = false);
WXDLLIMPEXP_BASE void wxDebugFree(void * buf, bool isVect = false);
}
#endif // __VISUALC__>=1200
#endif // wxUSE_GLOBAL_MEMORY_OPERATORS
-#endif // __WXDEBUG__
//**********************************************************************************
#define WXTRACE wxTrace
#define WXTRACELEVEL wxTraceLevel
-#else // (defined(__WXDEBUG__) && wxUSE_MEMORY_TRACING) || wxUSE_DEBUG_CONTEXT
+#else // wxUSE_MEMORY_TRACING) || wxUSE_DEBUG_CONTEXT
#define WXDEBUG_DUMPDELAYCOUNTER
#define WXTRACE true ? (void)0 : wxTrace
#define WXTRACELEVEL true ? (void)0 : wxTraceLevel
-#endif // (defined(__WXDEBUG__) && wxUSE_MEMORY_TRACING) || wxUSE_DEBUG_CONTEXT
+#endif // wxUSE_MEMORY_TRACING) || wxUSE_DEBUG_CONTEXT
-#endif
- // _WX_MEMORYH__
+#endif // _WX_MEMORY_H_
// change the dialog style flag
void SetMessageDialogStyle(long style)
{
-#ifdef __WXDEBUG__
wxASSERT_MSG( ((style & wxYES_NO) == wxYES_NO) || !(style & wxYES_NO),
"wxYES and wxNO may only be used together" );
if ((style & wxCANCEL_DEFAULT) != 0 && (style & wxNO_DEFAULT) != 0)
wxFAIL_MSG("only one default button can be specified");
-#endif
m_dialogStyle = style;
}
void SetHBITMAP(WXHBITMAP bmp) { SetHandle((WXHANDLE)bmp); }
WXHBITMAP GetHBITMAP() const { return (WXHBITMAP)GetHandle(); }
-#ifdef __WXDEBUG__
void SetSelectedInto(wxDC *dc);
wxDC *GetSelectedInto() const;
-#endif // __WXDEBUG__
protected:
virtual wxGDIImageRefData *CreateData() const;
{
if ( m_hGlobal && !GlobalUnlock(m_hGlobal) )
{
-#ifdef __WXDEBUG__
// this might happen simply because the block became unlocked
DWORD dwLastError = ::GetLastError();
if ( dwLastError != NO_ERROR )
{
wxLogApiError(_T("GlobalUnlock"), dwLastError);
}
-#endif // __WXDEBUG__
}
}
#define wxDynamicCastThis(className) \
(IsKindOf(&className::ms_classInfo) ? (className *)(this) : (className *)0)
-#ifdef __WXDEBUG__
-inline void* wxCheckCast(void *ptr)
+// FIXME-VC6: dummy argument needed because VC6 doesn't support explicitly
+// choosing the template function to call
+template <class T>
+inline T *wxCheckCast(const void *ptr, T * = NULL)
{
- wxASSERT_MSG( ptr, _T("wxStaticCast() used incorrectly") );
- return ptr;
+ wxASSERT_MSG( wxDynamicCast(ptr, T), "wxStaticCast() used incorrectly" );
+ return const_cast<T *>(static_cast<const T *>(ptr));
}
-#define wxStaticCast(obj, className) \
- ((className *)wxCheckCast(wxDynamicCast(obj, className)))
-
-#else // !__WXDEBUG__
-#define wxStaticCast(obj, className) \
- const_cast<className *>(static_cast<const className *>(obj))
-#endif // __WXDEBUG__
+#define wxStaticCast(obj, className) wxCheckCast((obj), (className *)NULL)
// ----------------------------------------------------------------------------
// set up memory debugging macros
_WX_WANT_ARRAY_DELETE_VOID_WXCHAR_INT = void operator delete[] (void* buf, wxChar*, int )
*/
-#if defined(__WXDEBUG__) && wxUSE_MEMORY_TRACING
+#if wxUSE_MEMORY_TRACING
// All compilers get this one
#define _WX_WANT_NEW_SIZET_WXCHAR_INT
#endif // wxUSE_ARRAY_MEMORY_OPERATORS
-#endif // __WXDEBUG__ && wxUSE_MEMORY_TRACING
+#endif // wxUSE_MEMORY_TRACING
// ----------------------------------------------------------------------------
// wxObjectRefData: ref counted data meant to be stored in wxObject
// more debugging macros
// ----------------------------------------------------------------------------
-// Redefine new to be the debugging version. This doesn't work with all
-// compilers, in which case you need to use WXDEBUG_NEW explicitly if you wish
-// to use the debugging version.
-
-#ifdef __WXDEBUG__
+#if wxUSE_DEBUG_NEW_ALWAYS
#define WXDEBUG_NEW new(__TFILE__,__LINE__)
- #if wxUSE_DEBUG_NEW_ALWAYS
- #if wxUSE_GLOBAL_MEMORY_OPERATORS
- #define new WXDEBUG_NEW
- #elif defined(__VISUALC__)
- // Including this file redefines new and allows leak reports to
- // contain line numbers
- #include "wx/msw/msvcrt.h"
- #endif
- #endif // wxUSE_DEBUG_NEW_ALWAYS
-#else // !__WXDEBUG__
- #define WXDEBUG_NEW new
-#endif // __WXDEBUG__/!__WXDEBUG__
+ #if wxUSE_GLOBAL_MEMORY_OPERATORS
+ #define new WXDEBUG_NEW
+ #elif defined(__VISUALC__)
+ // Including this file redefines new and allows leak reports to
+ // contain line numbers
+ #include "wx/msw/msvcrt.h"
+ #endif
+#endif // wxUSE_DEBUG_NEW_ALWAYS
#endif // _WX_OBJECTH__
void SetHBITMAP(WXHBITMAP bmp) { SetHandle((WXHANDLE)bmp); }
WXHBITMAP GetHBITMAP() const { return (WXHBITMAP)GetHandle(); }
-#ifdef __WXDEBUG__
- void SetSelectedInto(wxDC *dc);
- wxDC *GetSelectedInto() const;
-#endif // __WXDEBUG__
-
protected:
// common part of all ctors
void Init();
int m_extraStyle; // global extra style
-#ifdef __WXDEBUG__
int m_warnings;
-#endif
int HasExtraStyle( int style ) const { return (m_extraStyle & style); }
};
*/
void CorrectEditorWidgetPosY();
-#ifdef __WXDEBUG__
- void _log_items();
- void OnScreenNote( const wxChar* format, ... );
-#endif
-
/** Deselect current selection, if any. Returns true if success
(ie. validator did not intercept). */
bool DoClearSelection();
// checks correctness of UTF-8 sequence
static bool IsValidUtf8String(const char *c,
size_t len = wxStringImpl::npos);
-#ifdef __WXDEBUG__
- static bool IsValidUtf8LeadByte(unsigned char c);
-#endif
+ static bool IsValidUtf8LeadByte(unsigned char c)
+ {
+ return (c <= 0x7F) || (c >= 0xC2 && c <= 0xF4);
+ }
// table of offsets to skip forward when iterating over UTF-8 sequence
static const unsigned char ms_utf8IterTable[256];
wxArrayString& desc) const;
#endif // __WXGTK20____
-#if defined(__WXDEBUG__) && defined(__WXGTK20__)
+#if defined(__WXGTK20__)
virtual bool ShowAssertDialog(const wxString& msg);
#endif
// Processes an X event.
virtual bool ProcessXEvent(WXEvent* event);
-#ifdef __WXDEBUG__
- virtual void OnAssert(const wxChar *file, int line, const wxChar* cond, const wxChar *msg);
-#endif // __WXDEBUG__
-
public:
// Implementation
virtual bool Initialize(int& argc, wxChar **argv);
void wxAllocColor(Display *display,Colormap colormap,XColor *xcolor);
// For debugging
-#ifdef __WXDEBUG__
wxString wxGetXEventName(XEvent& event);
-#endif
// Is the window visible?
bool wxWindowIsVisible(Window win);
/** @addtogroup group_funcmacro_debug */
//@{
+/**
+ @def wxDEBUG_LEVEL
+
+ Preprocessor symbol defining the level of debug support available.
+
+ Currently wxDEBUG_LEVEL is 0 in release builds (__WXDEBUG__ not defined)
+ and 1 in debug builds (it is). In the immediate future this will change
+ however and this symbol will be defined directly as 0, 1 or 2 while
+ __WXDEBUG__ won't be used by wxWidgets any longer.
+
+ @header{wx/debug.h}
+ */
+#define wxDEBUG_LEVEL
+
+/**
+ Type for the function called in case of assert failure.
+
+ @see wxSetAssertHandler()
+ */
+typedef void (*wxAssertHandler_t)(const wxString& file,
+ int line,
+ const wxString& func,
+ const wxString& cond,
+ const wxString& msg);
+
/**
Assert macro. An error message will be generated if the condition is @false in
debug mode, but nothing will be done in the release build.
*/
#define wxASSERT( condition )
+/**
+ Assert macro for expensive run-time checks.
+
+ This macro does nothing unless wxDEBUG_LEVEL is 2 or more and is meant to
+ be used for the assertions with noticeable performance impact and which,
+ hence, should be disabled during run-time.
+
+ If wxDEBUG_LEVEL is 2 or more, it becomes the same as wxASSERT().
+
+ @header{wx/debug.h}
+ */
+#define wxASSERT_LEVEL_2( condition )
+
+/**
+ Assert macro with a custom message for expensive run-time checks.
+
+ If wxDEBUG_LEVEL is 2 or more, this is the same as wxASSERT_MSG(),
+ otherwise it doesn't do anything at all.
+
+ @see wxASSERT_LEVEL_2()
+
+ @header{wx/debug.h}
+ */
+#define wxASSERT_LEVEL_2_MSG( condition, msg)
+
+
/**
This macro results in a @ref wxCOMPILE_TIME_ASSERT "compile time assertion failure"
if the size of the given @c type is less than @c size bits.
*/
#define wxCOMPILE_TIME_ASSERT2(condition, message, name)
+/**
+ Disable the condition checks in the assertions.
+
+ This is the same as calling wxSetAssertHandler() with @NULL handler.
+ */
+void wxDisableAsserts();
+
/**
Will always generate an assert error if this code is reached (in debug mode).
Note that you don't have to (and cannot) use brackets when invoking this
bool wxIsDebuggerRunning();
/**
- This function is called whenever one of debugging macros fails (i.e.
- condition is @false in an assertion). It is only defined in the debug mode,
- in release builds the wxCHECK() failures don't result in anything.
+ Sets the function to be called in case of assertion failure.
+
+ The default assert handler forwards to wxApp::OnAssertFailure() whose
+ default behaviour is, in turn, to show the standard assertion failure
+ dialog if a wxApp object exists or shows the same dialog itself directly
+ otherwise.
+
+ While usually it is enough -- and more convenient -- to just override
+ OnAssertFailure(), to handle all assertion failures, including those
+ occurring even before wxApp object creation of after its destruction you
+ need to provide your assertion handler function.
+
+ This function also provides a simple way to disable all asserts: simply
+ pass @NULL pointer to it. Doing this will result in not even evaluating
+ assert conditions at all, avoiding almost all run-time cost of asserts.
- To override the default behaviour in the debug builds which is to show the
- user a dialog asking whether he wants to abort the program, continue or
- continue ignoring any subsequent assert failures, you may override
- wxApp::OnAssertFailure() which is called by this function if the global
- application object exists.
+ Notice that this function is not MT-safe, so you should call it before
+ starting any other threads.
+
+ The return value of this function is the previous assertion handler. It can
+ be called after any pre-processing by your handler and can also be restored
+ later if you uninstall your handler.
+
+ @param handler
+ The function to call in case of assertion failure or @NULL.
+ @return
+ The previous assert handler which is not @NULL by default but could be
+ @NULL if it had been previously set to this value using this function.
@header{wx/debug.h}
-*/
-void wxOnAssert( const char* fileName,
- int lineNumber,
- const char* function,
- const char* condition,
- const char* message = NULL );
+ */
+wxAssertHandler_t wxSetAssertHandler(wxAssertHandler_t handler);
/**
In debug mode (when @c __WXDEBUG__ is defined) this function generates a
{
m_topWindow = NULL;
-#ifdef __WXDEBUG__
- m_isInAssert = false;
-#endif // __WXDEBUG__
-
argc = 0;
#if !wxUSE_UNICODE
argv = NULL;
}
}
-#ifdef __WXDEBUG__
-void wxApp::OnAssert(const wxChar *file, int line, const wxChar* cond, const wxChar *msg)
-{
- m_isInAssert = true;
- wxAppBase::OnAssert(file, line, cond, msg);
- m_isInAssert = false;
-}
-#endif // __WXDEBUG__
-
/* A note about Cocoa's event loops vs. run loops:
It's important to understand that Cocoa has a two-level event loop. The
#include "wx/fontmap.h"
#endif // wxUSE_FONTMAP
-#ifdef __WXDEBUG__
+#if wxDEBUG_LEVEL
#if wxUSE_STACKWALKER
#include "wx/stackwalk.h"
#ifdef __WXMSW__
#endif // wxUSE_STACKWALKER
#include "wx/recguard.h"
-#endif // __WXDEBUG__
+#endif // wxDEBUG_LEVEL
// wxABI_VERSION can be defined when compiling applications but it should be
// left undefined when compiling the library itself, it is then set to its
// private functions prototypes
// ----------------------------------------------------------------------------
-#ifdef __WXDEBUG__
+#if wxDEBUG_LEVEL
// really just show the assert dialog
static bool DoShowAssertDialog(const wxString& msg);
// prepare for showing the assert dialog, use the given traits or
// DoShowAssertDialog() as last fallback to really show it
static
- void ShowAssertDialog(const wxString& szFile,
- int nLine,
- const wxString& szFunc,
- const wxString& szCond,
- const wxString& szMsg,
+ void ShowAssertDialog(const wxString& file,
+ int line,
+ const wxString& func,
+ const wxString& cond,
+ const wxString& msg,
wxAppTraits *traits = NULL);
+#endif // wxDEBUG_LEVEL
+#ifdef __WXDEBUG__
// turn on the trace masks specified in the env variable WXTRACE
static void LINKAGEMODE SetTraceMasks();
#endif // __WXDEBUG__
return true;
}
-#ifdef __WXDEBUG__
-
void wxAppConsoleBase::OnAssertFailure(const wxChar *file,
int line,
const wxChar *func,
const wxChar *cond,
const wxChar *msg)
{
+#if wxDEBUG_LEVEL
ShowAssertDialog(file, line, func, cond, msg, GetTraits());
+#else
+ // this function is still present even in debug level 0 build for ABI
+ // compatibility reasons but is never called there and so can simply do
+ // nothing in it
+ wxUnusedVar(file);
+ wxUnusedVar(line);
+ wxUnusedVar(func);
+ wxUnusedVar(cond);
+ wxUnusedVar(msg);
+#endif // wxDEBUG_LEVEL/!wxDEBUG_LEVEL
}
void wxAppConsoleBase::OnAssert(const wxChar *file,
OnAssertFailure(file, line, NULL, cond, msg);
}
-#endif // __WXDEBUG__
-
// ============================================================================
// other classes implementations
// ============================================================================
return NULL;
}
-#ifdef __WXDEBUG__
bool wxConsoleAppTraitsBase::ShowAssertDialog(const wxString& msg)
{
return wxAppTraitsBase::ShowAssertDialog(msg);
}
-#endif
bool wxConsoleAppTraitsBase::HasStderr()
{
}
#endif // wxUSE_THREADS
-#ifdef __WXDEBUG__
-
bool wxAppTraitsBase::ShowAssertDialog(const wxString& msgOriginal)
{
+#if wxDEBUG_LEVEL
wxString msg = msgOriginal;
#if wxUSE_STACKWALKER
#endif // wxUSE_STACKWALKER
return DoShowAssertDialog(msg);
+#else // !wxDEBUG_LEVEL
+ wxUnusedVar(msgOriginal);
+
+ return false;
+#endif // wxDEBUG_LEVEL/!wxDEBUG_LEVEL
}
#if wxUSE_STACKWALKER
wxString wxAppTraitsBase::GetAssertStackTrace()
{
+#if wxDEBUG_LEVEL
wxString stackTrace;
class StackDump : public wxStackWalker
stackTrace = stackTrace.BeforeLast(wxT('\n'));
return stackTrace;
+#else // !wxDEBUG_LEVEL
+ // this function is still present for ABI-compatibility even in debug level
+ // 0 build but is not used there and so can simply do nothing
+ return wxString();
+#endif // wxDEBUG_LEVEL/!wxDEBUG_LEVEL
}
#endif // wxUSE_STACKWALKER
-#endif // __WXDEBUG__
-
// ============================================================================
// global functions implementation
// ============================================================================
//else: do nothing, what can we do?
}
-#ifdef __WXDEBUG__
-
// wxASSERT() helper
bool wxAssertIsEqual(int x, int y)
{
return x == y;
}
+#if wxDEBUG_LEVEL
+
// break into the debugger
void wxTrap()
{
#endif // Win/Unix
}
-// this function is called when an assert fails
-static void wxDoOnAssert(const wxString& szFile,
- int nLine,
- const wxString& szFunc,
- const wxString& szCond,
- const wxString& szMsg = wxEmptyString)
+// default assert handler
+static void
+wxDefaultAssertHandler(const wxString& file,
+ int line,
+ const wxString& func,
+ const wxString& cond,
+ const wxString& msg)
{
// FIXME MT-unsafe
static int s_bInAssert = 0;
{
// by default, show the assert dialog box -- we can't customize this
// behaviour
- ShowAssertDialog(szFile, nLine, szFunc, szCond, szMsg);
+ ShowAssertDialog(file, line, func, cond, msg);
}
else
{
// let the app process it as it wants
// FIXME-UTF8: use wc_str(), not c_str(), when ANSI build is removed
- wxTheApp->OnAssertFailure(szFile.c_str(), nLine, szFunc.c_str(),
- szCond.c_str(), szMsg.c_str());
+ wxTheApp->OnAssertFailure(file.c_str(), line, func.c_str(),
+ cond.c_str(), msg.c_str());
}
}
-void wxOnAssert(const wxString& szFile,
- int nLine,
- const wxString& szFunc,
- const wxString& szCond,
- const wxString& szMsg)
+wxAssertHandler_t wxTheAssertHandler = wxDefaultAssertHandler;
+
+void wxOnAssert(const wxString& file,
+ int line,
+ const wxString& func,
+ const wxString& cond,
+ const wxString& msg)
{
- wxDoOnAssert(szFile, nLine, szFunc, szCond, szMsg);
+ wxTheAssertHandler(file, line, func, cond, msg);
}
-void wxOnAssert(const wxString& szFile,
- int nLine,
- const wxString& szFunc,
- const wxString& szCond)
+void wxOnAssert(const wxString& file,
+ int line,
+ const wxString& func,
+ const wxString& cond)
{
- wxDoOnAssert(szFile, nLine, szFunc, szCond);
+ wxTheAssertHandler(file, line, func, cond, wxString());
}
-void wxOnAssert(const wxChar *szFile,
- int nLine,
- const char *szFunc,
- const wxChar *szCond,
- const wxChar *szMsg)
+void wxOnAssert(const wxChar *file,
+ int line,
+ const char *func,
+ const wxChar *cond,
+ const wxChar *msg)
{
- wxDoOnAssert(szFile, nLine, szFunc, szCond, szMsg);
+ // this is the backwards-compatible version (unless we don't use Unicode)
+ // so it could be called directly from the user code and this might happen
+ // even when wxTheAssertHandler is NULL
+#if wxUSE_UNICODE
+ if ( wxTheAssertHandler )
+#endif // wxUSE_UNICODE
+ wxTheAssertHandler(file, line, func, cond, msg);
}
-void wxOnAssert(const char *szFile,
- int nLine,
- const char *szFunc,
- const char *szCond,
- const wxString& szMsg)
+void wxOnAssert(const char *file,
+ int line,
+ const char *func,
+ const char *cond,
+ const wxString& msg)
{
- wxDoOnAssert(szFile, nLine, szFunc, szCond, szMsg);
+ wxTheAssertHandler(file, line, func, cond, msg);
}
-void wxOnAssert(const char *szFile,
- int nLine,
- const char *szFunc,
- const char *szCond,
+void wxOnAssert(const char *file,
+ int line,
+ const char *func,
+ const char *cond,
const wxCStrData& msg)
{
- wxDoOnAssert(szFile, nLine, szFunc, szCond, msg);
+ wxTheAssertHandler(file, line, func, cond, msg);
}
#if wxUSE_UNICODE
-void wxOnAssert(const char *szFile,
- int nLine,
- const char *szFunc,
- const char *szCond)
+void wxOnAssert(const char *file,
+ int line,
+ const char *func,
+ const char *cond)
{
- wxDoOnAssert(szFile, nLine, szFunc, szCond);
+ wxTheAssertHandler(file, line, func, cond, wxString());
}
-void wxOnAssert(const char *szFile,
- int nLine,
- const char *szFunc,
- const char *szCond,
- const char *szMsg)
+void wxOnAssert(const char *file,
+ int line,
+ const char *func,
+ const char *cond,
+ const char *msg)
{
- wxDoOnAssert(szFile, nLine, szFunc, szCond, szMsg);
+ wxTheAssertHandler(file, line, func, cond, msg);
}
-void wxOnAssert(const char *szFile,
- int nLine,
- const char *szFunc,
- const char *szCond,
- const wxChar *szMsg)
+void wxOnAssert(const char *file,
+ int line,
+ const char *func,
+ const char *cond,
+ const wxChar *msg)
{
- wxDoOnAssert(szFile, nLine, szFunc, szCond, szMsg);
+ wxTheAssertHandler(file, line, func, cond, msg);
}
#endif // wxUSE_UNICODE
-#endif // __WXDEBUG__
+#endif // wxDEBUG_LEVEL
// ============================================================================
// private functions implementation
#endif // wxUSE_LOG
}
+#endif // __WXDEBUG__
+
+#if wxDEBUG_LEVEL
+
static
bool DoShowAssertDialog(const wxString& msg)
{
#if defined(__WXMSW__) && !defined(__WXMICROWIN__)
wxString msgDlg(msg);
- // this message is intentionally not translated -- it is for
- // developpers only
+ // this message is intentionally not translated -- it is for developers
+ // only -- and the less code we use here, less is the danger of recursively
+ // asserting and dying
msgDlg += wxT("\nDo you want to stop the program?\n")
wxT("You can also choose [Cancel] to suppress ")
wxT("further warnings.");
return false;
}
-// show the assert modal dialog
+// show the standard assert dialog
static
-void ShowAssertDialog(const wxString& szFile,
- int nLine,
- const wxString& szFunc,
- const wxString& szCond,
- const wxString& szMsg,
+void ShowAssertDialog(const wxString& file,
+ int line,
+ const wxString& func,
+ const wxString& cond,
+ const wxString& msgUser,
wxAppTraits *traits)
{
// this variable can be set to true to suppress "assert failure" messages
// make life easier for people using VC++ IDE by using this format: like
// this, clicking on the message will take us immediately to the place of
// the failed assert
- msg.Printf(wxT("%s(%d): assert \"%s\" failed"), szFile, nLine, szCond);
+ msg.Printf(wxT("%s(%d): assert \"%s\" failed"), file, line, cond);
// add the function name, if any
- if ( !szFunc.empty() )
- msg << _T(" in ") << szFunc << _T("()");
+ if ( !func.empty() )
+ msg << _T(" in ") << func << _T("()");
// and the message itself
- if ( !szMsg.empty() )
+ if ( !msgUser.empty() )
{
- msg << _T(": ") << szMsg;
+ msg << _T(": ") << msgUser;
}
else // no message given
{
}
}
-#endif // __WXDEBUG__
+#endif // wxDEBUG_LEVEL
return (left.GetID() == right.GetID() );
}
-#ifdef __WXDEBUG__
-void wxDataViewItem::Print(const wxString& text) const
-{
- wxPrintf(wxT("item %s: %lu\n"), text.GetData(), wxPtrToUInt(m_id));
-}
-#endif
-
// ---------------------------------------------------------
// wxDataViewModelNotifier
// ---------------------------------------------------------
// the memory leaks when using it, however this breaks re-initializing the
// library (i.e. repeated calls to wxInitialize/wxUninitialize) because the
// event tables won't be rebuilt the next time, so disable this by default
-#if defined(__WXDEBUG__) && wxUSE_MEMORY_TRACING
+#if wxUSE_MEMORY_TRACING
class wxEventTableEntryModule: public wxModule
{
IMPLEMENT_DYNAMIC_CLASS(wxEventTableEntryModule, wxModule)
-#endif // __WXDEBUG__ && wxUSE_MEMORY_TRACING
+#endif // wxUSE_MEMORY_TRACING
// ----------------------------------------------------------------------------
// global variables
m_size = 0;
}
-#if defined(__WXDEBUG__) && wxUSE_MEMORY_TRACING
+#if wxUSE_MEMORY_TRACING
// Clear all tables
void wxEventHashTable::ClearAll()
}
}
-#endif // __WXDEBUG__ && wxUSE_MEMORY_TRACING
+#endif // wxUSE_MEMORY_TRACING
bool wxEventHashTable::HandleEvent(wxEvent &event, wxEvtHandler *self)
{
// wxHyperlinkCtrlBase
// ----------------------------------------------------------------------------
-#ifdef __WXDEBUG__
-void wxHyperlinkCtrlBase::CheckParams(const wxString& label, const wxString& url, long style)
+void
+wxHyperlinkCtrlBase::CheckParams(const wxString& label,
+ const wxString& url,
+ long style)
{
+#if wxDEBUG_LEVEL
wxASSERT_MSG(!url.empty() || !label.empty(),
wxT("Both URL and label are empty ?"));
(int)((style & wxHL_ALIGN_RIGHT) != 0);
wxASSERT_MSG(alignment == 1,
wxT("Specify exactly one align flag!"));
+#else // !wxDEBUG_LEVEL
+ wxUnusedVar(label);
+ wxUnusedVar(url);
+ wxUnusedVar(style);
+#endif // wxDEBUG_LEVEL/!wxDEBUG_LEVEL
}
-#endif
void wxHyperlinkCtrlBase::SendEvent()
{
void wxProtocolLog::DoLogString(const wxString& str)
{
+ wxUnusedVar(str); // unused if wxLogTrace() is disabled
wxLogTrace(m_traceMask, "%s", str);
}
return true;
}
-#ifdef __WXDEBUG__
-bool wxStringOperationsUtf8::IsValidUtf8LeadByte(unsigned char c)
-{
- return (c <= 0x7F) || (c >= 0xC2 && c <= 0xF4);
-}
-#endif
-
-
// NB: this is in this file and not unichar.cpp to keep all UTF-8 encoding
// code in single place
wxUniChar::Utf8CharBuffer wxUniChar::AsUTF8() const
id_save = m_idleSourceId;
m_idleSourceId = 0;
wx_add_idle_hooks();
-#ifdef __WXDEBUG__
+
+#if wxDEBUG_LEVEL
// don't generate the idle events while the assert modal dialog is shown,
// this matches the behavior of wxMSW
if (m_isInAssert)
wxApp::wxApp()
{
-#ifdef __WXDEBUG__
m_isInAssert = false;
-#endif // __WXDEBUG__
+
#if wxUSE_THREADS
m_idleMutex = NULL;
#endif
return gtk_events_pending() != 0;
}
-#ifdef __WXDEBUG__
-
void wxApp::OnAssertFailure(const wxChar *file,
int line,
const wxChar* func,
const wxChar* cond,
const wxChar *msg)
{
-
+ // there is no need to do anything if asserts are disabled in this build
+ // anyhow
+#if wxDEBUG_LEVEL
// block wx idle events while assert dialog is showing
m_isInAssert = true;
wxAppBase::OnAssertFailure(file, line, func, cond, msg);
m_isInAssert = false;
+#else // !wxDEBUG_LEVEL
+ wxUnusedVar(file);
+ wxUnusedVar(line);
+ wxUnusedVar(func);
+ wxUnusedVar(cond);
+ wxUnusedVar(msg);
+#endif // wxDEBUG_LEVEL/!wxDEBUG_LEVEL
}
-#endif // __WXDEBUG__
-
#if wxUSE_THREADS
void wxGUIAppTraits::MutexGuiEnter()
{
case wxNO_OP: mode = GDK_NOOP; break;
case wxSRC_INVERT: mode = GDK_COPY_INVERT; break;
case wxNOR: mode = GDK_NOR; break;
+ default:
+ wxFAIL_MSG("unknown mode");
+ return;
}
m_logicalFunction = function;
if (!wxTheApp)
return TRUE;
-#ifdef __WXDEBUG__
+#if wxDEBUG_LEVEL
// don't generate the idle events while the assert modal dialog is shown,
// this completely confuses the apps which don't expect to be reentered
// from some safely-looking functions
}
return TRUE;
}
-#endif // __WXDEBUG__
+#endif // wxDEBUG_LEVEL
// When getting called from GDK's time-out handler
// we are no longer within GDK's grab on the GUI
wxApp::wxApp()
{
-#ifdef __WXDEBUG__
m_isInAssert = false;
-#endif // __WXDEBUG__
m_idleTag = 0;
g_isIdle = TRUE;
wxAppBase::CleanUp();
}
-#ifdef __WXDEBUG__
-
-void wxApp::OnAssert(const wxChar *file, int line, const wxChar* cond, const wxChar *msg)
+void wxApp::OnAssertFailure(const wxChar *file,
+ int line,
+ const wxChar* func,
+ const wxChar* cond,
+ const wxChar *msg)
{
+ // there is no need to do anything if asserts are disabled in this build
+ // anyhow
+#if wxDEBUG_LEVEL
+ // block wx idle events while assert dialog is showing
m_isInAssert = true;
- wxAppBase::OnAssert(file, line, cond, msg);
+ wxAppBase::OnAssertFailure(file, line, func, cond, msg);
m_isInAssert = false;
+#else // !wxDEBUG_LEVEL
+ wxUnusedVar(file);
+ wxUnusedVar(line);
+ wxUnusedVar(func);
+ wxUnusedVar(cond);
+ wxUnusedVar(msg);
+#endif // wxDEBUG_LEVEL/!wxDEBUG_LEVEL
}
-#endif // __WXDEBUG__
-
void wxApp::RemoveIdleTag()
{
#if wxUSE_THREADS
// MSW-specific
// ------------
-#ifdef __WXDEBUG__
+#if wxDEBUG_LEVEL
// this field is solely for error checking: we detect selecting a bitmap
// into more than one DC at once or deleting a bitmap still selected into a
// DC (both are serious programming errors under Windows)
wxDC *m_selectedInto;
-#endif // __WXDEBUG__
+#endif // wxDEBUG_LEVEL
#if wxUSE_WXDIB
// when GetRawData() is called for a DDB we need to convert it to a DIB
wxBitmapRefData::wxBitmapRefData()
{
-#ifdef __WXDEBUG__
+#if wxDEBUG_LEVEL
m_selectedInto = NULL;
#endif
m_bitmapMask = NULL;
wxBitmapRefData::wxBitmapRefData(const wxBitmapRefData& data)
: wxGDIImageRefData(data)
{
-#ifdef __WXDEBUG__
+#if wxDEBUG_LEVEL
m_selectedInto = NULL;
#endif
return bmp;
}
-#ifdef __WXDEBUG__
-
wxDC *wxBitmap::GetSelectedInto() const
{
+#if wxDEBUG_LEVEL
return GetBitmapData() ? GetBitmapData()->m_selectedInto : NULL;
-}
-
+#else
+ return NULL;
#endif
+}
void wxBitmap::UseAlpha()
{
// wxBitmap setters
// ----------------------------------------------------------------------------
-#ifdef __WXDEBUG__
-
void wxBitmap::SetSelectedInto(wxDC *dc)
{
+#if wxDEBUG_LEVEL
if ( GetBitmapData() )
GetBitmapData()->m_selectedInto = dc;
-}
-
+#else
+ wxUnusedVar(dc);
#endif
+}
#if wxUSE_PALETTE
static PAINTSTRUCT g_paintStruct;
-#ifdef __WXDEBUG__
+#ifdef wxHAS_PAINT_DEBUG
// a global variable which we check to verify that wxPaintDC are only
// created in response to WM_PAINT message - doing this from elsewhere is a
// common programming error among wxWidgets programmers and might lead to
// very subtle and difficult to debug refresh/repaint bugs.
int g_isPainting = 0;
-#endif // __WXDEBUG__
+#endif // wxHAS_PAINT_DEBUG
// ===========================================================================
// implementation
{
wxCHECK_RET( window, wxT("NULL canvas in wxPaintDCImpl ctor") );
-#ifdef __WXDEBUG__
+#ifdef wxHAS_PAINT_DEBUG
if ( g_isPainting <= 0 )
{
wxFAIL_MSG( wxT("wxPaintDCImpl may be created only in EVT_PAINT handler!") );
static RECT g_paintStruct;
-#ifdef __WXDEBUG__
+#ifdef wxHAS_PAINT_DEBUG
// a global variable which we check to verify that wxPaintDC are only
// created in resopnse to WM_PAINT message - doing this from elsewhere is a
// common programming error among wxWidgets programmers and might lead to
// very subtle and difficult to debug refresh/repaint bugs.
int g_isPainting = 0;
-#endif // __WXDEBUG__
+#endif // wxHAS_PAINT_DEBUG
// ===========================================================================
// implementation
{
wxCHECK_RET(pCanvas, wxT("NULL canvas in wxPaintDC ctor"));
-#ifdef __WXDEBUG__
+#ifdef wxHAS_PAINT_DEBUG
if (g_isPainting <= 0)
{
wxFAIL_MSG( wxT("wxPaintDC may be created only in EVT_PAINT handler!") );
wxPalette m_bitmapPalette;
#endif // wxUSE_PALETTE
-#ifdef __WXDEBUG__
- wxDC *m_selectedInto;
-#endif // __WXDEBUG__
-
#if wxUSE_WXDIB
wxDIB *m_dib;
#endif
wxBitmapRefData::wxBitmapRefData()
{
-#ifdef __WXDEBUG__
- m_selectedInto = NULL;
-#endif
m_bitmapMask = NULL;
m_hBitmap = (WXHBITMAP) NULL;
return NULL;
}
-#ifdef __WXDEBUG__
-
-wxDC *wxBitmap::GetSelectedInto() const
-{
- return NULL;
-}
-
-#endif
-
bool wxBitmap::HasAlpha() const
{
return false;
// wxBitmap setters
// ----------------------------------------------------------------------------
-#ifdef __WXDEBUG__
-
-void wxBitmap::SetSelectedInto(wxDC *dc)
-{
-}
-
-#endif
-
#if wxUSE_PALETTE
void wxBitmap::SetPalette(const wxPalette& palette)
wxVariant v;
- // Prepare some shared variants
+ // Prepare some shared variants
m_vEmptyString = wxString();
m_vZero = (long) 0;
m_vMinusOne = (long) -1;
m_strUnits = wxS("Units");
m_strInlineHelp = wxS("InlineHelp");
-#ifdef __WXDEBUG__
m_warnings = 0;
-#endif
}
#endif
#ifndef wxPG_ICON_WIDTH
- m_expandbmp = NULL;
- m_collbmp = NULL;
- m_iconWidth = 11;
- m_iconHeight = 11;
+ m_expandbmp = NULL;
+ m_collbmp = NULL;
+ m_iconWidth = 11;
+ m_iconHeight = 11;
#else
m_iconWidth = wxPG_ICON_WIDTH;
#endif
#ifndef wxPG_ICON_WIDTH
// create two bitmap nodes for drawing
- m_expandbmp = new wxBitmap(expand_xpm);
- m_collbmp = new wxBitmap(collapse_xpm);
+ m_expandbmp = new wxBitmap(expand_xpm);
+ m_collbmp = new wxBitmap(collapse_xpm);
- // calculate average font height for bitmap centering
+ // calculate average font height for bitmap centering
- m_iconWidth = m_expandbmp->GetWidth();
- m_iconHeight = m_expandbmp->GetHeight();
+ m_iconWidth = m_expandbmp->GetWidth();
+ m_iconHeight = m_expandbmp->GetHeight();
#endif
m_curcursor = wxCURSOR_ARROW;
m_cursorSizeWE = new wxCursor( wxCURSOR_SIZEWE );
- // adjust bitmap icon y position so they are centered
+ // adjust bitmap icon y position so they are centered
m_vspacing = wxPG_DEFAULT_VSPACING;
CalculateFontAndBitmapStuff( wxPG_DEFAULT_VSPACING );
m_tlwHandler = handler;
m_tlp->PushEventHandler(handler);
- // set virtual size to this window size
+ // set virtual size to this window size
wxSize wndsize = GetSize();
- SetVirtualSize(wndsize.GetWidth(), wndsize.GetWidth());
+ SetVirtualSize(wndsize.GetWidth(), wndsize.GetWidth());
m_timeCreated = ::wxGetLocalTimeMillis();
delete m_cursorSizeWE;
#ifndef wxPG_ICON_WIDTH
- delete m_expandbmp;
- delete m_collbmp;
+ delete m_expandbmp;
+ delete m_collbmp;
#endif
// Delete common value records
void wxPropertyGrid::CalculateFontAndBitmapStuff( int vspacing )
{
- int x = 0, y = 0;
+ int x = 0, y = 0;
m_captionFont = wxScrolledWindow::GetFont();
- GetTextExtent(wxS("jG"), &x, &y, 0, 0, &m_captionFont);
+ GetTextExtent(wxS("jG"), &x, &y, 0, 0, &m_captionFont);
m_subgroup_extramargin = x + (x/2);
- m_fontHeight = y;
+ m_fontHeight = y;
#if wxPG_USE_RENDERER_NATIVE
m_iconWidth = wxPG_ICON_WIDTH;
m_marginWidth = m_gutterWidth*2 + m_iconWidth;
m_captionFont.SetWeight(wxBOLD);
- GetTextExtent(wxS("jG"), &x, &y, 0, 0, &m_captionFont);
+ GetTextExtent(wxS("jG"), &x, &y, 0, 0, &m_captionFont);
m_lineHeight = m_fontHeight+(2*m_spacingy)+1;
GetClientSize(&width,&height);
// Now adjust virtual size.
- SetVirtualSize(x, y);
+ SetVirtualSize(x, y);
int xAmount = 0;
int xPos = 0;
if ( space )
{
int tw, th;
- GetTextExtent( tipString, &tw, &th, 0, 0 );
+ GetTextExtent( tipString, &tw, &th, 0, 0 );
if ( tw > space )
{
SetToolTip( tipString );
}
}
-#ifdef __WXDEBUG__
+#if wxDEBUG_LEVEL
// Warn for identical names in debug mode.
if ( BaseGetPropertyByName(property->GetName()) &&
(!scheduledParent || scheduledParent->IsCategory()) )
{
- wxLogError(wxT("wxPropertyGrid: Warning - item with name \"%s\" already exists."),
- property->GetName().c_str());
+ wxFAIL_MSG(wxString::Format(
+ "wxPropertyGrid item with name \"%s\" already exists",
+ property->GetName()));
+
wxPGGlobalVars->m_warnings++;
}
-#endif
+#endif // wxDEBUG_LEVEL
// Make sure nothing is selected.
if ( propGrid )
// X11 error handling
//------------------------------------------------------------------------
-#ifdef __WXDEBUG__
typedef int (*XErrorHandlerFunc)(Display *, XErrorEvent *);
XErrorHandlerFunc gs_pfnXErrorHandler = 0;
else
return 0;
}
-#endif // __WXDEBUG__
//------------------------------------------------------------------------
// wxApp
bool wxApp::Initialize(int& argC, wxChar **argV)
{
-#if defined(__WXDEBUG__) && !wxUSE_NANOX
+#if !wxUSE_NANOX
// install the X error handler
gs_pfnXErrorHandler = XSetErrorHandler( wxXErrorHandler );
-#endif // __WXDEBUG__
+#endif
wxString displayName;
bool syncDisplay = false;
return false;
}
-#ifdef __WXDEBUG__
- wxString windowClass = win->GetClassInfo()->GetClassName();
-#endif
switch (event->type)
{
}
#if !wxUSE_NANOX
case PropertyNotify:
- {
- //wxLogDebug("PropertyNotify: %s", windowClass.c_str());
return HandlePropertyChange(_event);
- }
+
case ClientMessage:
{
if (!win->IsEnabled())
return win->HandleWindowEvent(focusEvent);
}
return false;
-
-#ifdef __WXDEBUG__
- default:
- //wxString eventName = wxGetXEventName(XEvent& event);
- //wxLogDebug(wxT("Event %s not handled"), eventName.c_str());
- break;
-#endif // __WXDEBUG__
}
return false;
wxAppConsole::Exit();
}
-#ifdef __WXDEBUG__
-
-void wxApp::OnAssert(const wxChar *file, int line, const wxChar* cond, const wxChar *msg)
-{
- // While the GUI isn't working that well, just print out the
- // message.
-#if 1
- wxAppBase::OnAssert(file, line, cond, msg);
-#else
- wxString msg2;
- msg2.Printf("At file %s:%d: %s", file, line, msg);
- wxLogDebug(msg2);
-#endif
-}
-
-#endif // __WXDEBUG__
}
}
-#ifdef __WXDEBUG__
wxString wxGetXEventName(XEvent& event)
{
#if wxUSE_NANOX
return wxString::FromAscii(event_name[type]);
#endif
}
-#endif
bool wxWindowIsVisible(Window win)
{
///////////////////////////////////////////////////////////////////////////////
// Name: tests/misc/misctests.cpp
// Purpose: test miscellaneous stuff
-// Author: Peter Most
+// Author: Peter Most, Vadim Zeitlin
// Created: 2008-07-10
// RCS-ID: $Id$
// Copyright: (c) 2008 Peter Most
+// (c) 2009 Vadim Zeitlin
///////////////////////////////////////////////////////////////////////////////
// ----------------------------------------------------------------------------
private:
CPPUNIT_TEST_SUITE( MiscTestCase );
+ CPPUNIT_TEST( Assert );
CPPUNIT_TEST( Delete );
CPPUNIT_TEST_SUITE_END();
+ void Assert();
void Delete();
DECLARE_NO_COPY_CLASS(MiscTestCase)
// also include in it's own registry so that these tests can be run alone
CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( MiscTestCase, "MiscTestCase" );
+namespace
+{
+
+void AssertIfOdd(int n)
+{
+ wxASSERT_MSG( !(n % 2), "parameter must be even" );
+}
+
+} // anonymous namespace
+
+void MiscTestCase::Assert()
+{
+ AssertIfOdd(0);
+ WX_ASSERT_FAILS_WITH_ASSERT(AssertIfOdd(1));
+
+ // doesn't fail any more
+ wxAssertHandler_t oldHandler = wxSetAssertHandler(NULL);
+ AssertIfOdd(17);
+ wxSetAssertHandler(oldHandler);
+}
+
void MiscTestCase::Delete()
{
// Allocate some arbitrary memory to get a valid pointer:
class TestAssertFailure { };
// macro to use for the functions which are supposed to fail an assertion
-#ifdef __WXDEBUG__
+#if wxDEBUG_LEVEL
// some old cppunit versions don't define CPPUNIT_ASSERT_THROW so roll our
// own
#define WX_ASSERT_FAILS_WITH_ASSERT(cond) \
CPPUNIT_FAIL("expected assertion not generated"); \
}
#else
- // there are no assertions in non-debug build so just check that it fails
+ // there are no assertions in this build so just check that it fails
#define WX_ASSERT_FAILS_WITH_ASSERT(cond) CPPUNIT_ASSERT(!(cond))
#endif