+// ----------------------------------------------------------------------------
+// clean up
+// ----------------------------------------------------------------------------
+
+// cleanup done before destroying wxTheApp
+static void DoCommonPreCleanup()
+{
+#if wxUSE_LOG
+ // flush the logged messages if any and install a 'safer' log target: the
+ // default one (wxLogGui) can't be used after the resources are freed just
+ // below and the user supplied one might be even more unsafe (using any
+ // wxWidgets GUI function is unsafe starting from now)
+ wxLog::DontCreateOnDemand();
+
+ // this will flush the old messages if any
+ delete wxLog::SetActiveTarget(new wxLogStderr);
+#endif // wxUSE_LOG
+}
+
+// cleanup done after destroying wxTheApp
+static void DoCommonPostCleanup()
+{
+ wxModule::CleanUpModules();
+
+ // we can't do this in wxApp itself because it doesn't know if argv had
+ // been allocated
+#if wxUSE_UNICODE
+ FreeConvertedArgs();
+#endif // wxUSE_UNICODE
+
+ // use Set(NULL) and not Get() to avoid creating a message output object on
+ // demand when we just want to delete it
+ delete wxMessageOutput::Set(NULL);
+
+#if wxUSE_LOG
+ // and now delete the last logger as well
+ delete wxLog::SetActiveTarget(NULL);
+#endif // wxUSE_LOG
+}
+
+void wxEntryCleanup()
+{
+ DoCommonPreCleanup();
+
+
+ // delete the application object
+ if ( wxTheApp )
+ {
+ wxTheApp->CleanUp();
+
+ // reset the global pointer to it to NULL before destroying it as in
+ // some circumstances this can result in executing the code using
+ // wxTheApp and using half-destroyed object is no good
+ wxAppConsole * const app = wxApp::GetInstance();
+ wxApp::SetInstance(NULL);
+ delete app;
+ }
+
+
+ DoCommonPostCleanup();
+}
+
+// ----------------------------------------------------------------------------
+// wxEntry
+// ----------------------------------------------------------------------------
+
+// for MSW the real wxEntry is defined in msw/main.cpp
+#ifndef __WXMSW__
+ #define wxEntryReal wxEntry
+#endif // !__WXMSW__
+
+int wxEntryReal(int& argc, wxChar **argv)
+{
+ // library initialization
+ if ( !wxEntryStart(argc, argv) )
+ {
+#if wxUSE_LOG
+ // flush any log messages explaining why we failed
+ delete wxLog::SetActiveTarget(NULL);
+#endif
+ return -1;
+ }
+
+ // if wxEntryStart succeeded, we must call wxEntryCleanup even if the code
+ // below returns or throws
+ wxCleanupOnExit cleanupOnExit;
+
+ WX_SUPPRESS_UNUSED_WARN(cleanupOnExit);
+
+ wxTRY
+ {
+
+ // app initialization
+ if ( !wxTheApp->CallOnInit() )
+ {
+ // don't call OnExit() if OnInit() failed
+ return -1;
+ }
+
+ // ensure that OnExit() is called if OnInit() had succeeded
+ class CallOnExit
+ {
+ public:
+ ~CallOnExit() { wxTheApp->OnExit(); }
+ } callOnExit;
+
+ WX_SUPPRESS_UNUSED_WARN(callOnExit);
+
+ // app execution
+ return wxTheApp->OnRun();
+ }
+ wxCATCH_ALL( wxTheApp->OnUnhandledException(); return -1; )
+}
+
+#if wxUSE_UNICODE
+
+// as with wxEntryStart, we provide an ANSI wrapper
+int wxEntry(int& argc, char **argv)
+{
+ ConvertArgsToUnicode(argc, argv);
+
+ return wxEntry(gs_initData.argc, gs_initData.argv);
+}
+
+#endif // wxUSE_UNICODE
+
+// ----------------------------------------------------------------------------
+// wxInitialize/wxUninitialize
+// ----------------------------------------------------------------------------
+
+bool wxInitialize(int argc, wxChar **argv)
+{
+ wxCRIT_SECT_LOCKER(lockInit, gs_initData.csInit);
+
+ if ( gs_initData.nInitCount++ )
+ {
+ // already initialized
+ return true;
+ }
+
+ return wxEntryStart(argc, argv);
+}
+
+void wxUninitialize()
+{
+ wxCRIT_SECT_LOCKER(lockInit, gs_initData.csInit);
+
+ if ( --gs_initData.nInitCount == 0 )
+ {
+ wxEntryCleanup();