00001 // $Id: ensure.cpp 1282 2006-06-09 09:46:49Z alex $ 00002 /* @@tag:xara-cn@@ DO NOT MODIFY THIS LINE 00003 ================================XARAHEADERSTART=========================== 00004 00005 Xara LX, a vector drawing and manipulation program. 00006 Copyright (C) 1993-2006 Xara Group Ltd. 00007 Copyright on certain contributions may be held in joint with their 00008 respective authors. See AUTHORS file for details. 00009 00010 LICENSE TO USE AND MODIFY SOFTWARE 00011 ---------------------------------- 00012 00013 This file is part of Xara LX. 00014 00015 Xara LX is free software; you can redistribute it and/or modify it 00016 under the terms of the GNU General Public License version 2 as published 00017 by the Free Software Foundation. 00018 00019 Xara LX and its component source files are distributed in the hope 00020 that it will be useful, but WITHOUT ANY WARRANTY; without even the 00021 implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 00022 See the GNU General Public License for more details. 00023 00024 You should have received a copy of the GNU General Public License along 00025 with Xara LX (see the file GPL in the root directory of the 00026 distribution); if not, write to the Free Software Foundation, Inc., 51 00027 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 00028 00029 00030 ADDITIONAL RIGHTS 00031 ----------------- 00032 00033 Conditional upon your continuing compliance with the GNU General Public 00034 License described above, Xara Group Ltd grants to you certain additional 00035 rights. 00036 00037 The additional rights are to use, modify, and distribute the software 00038 together with the wxWidgets library, the wxXtra library, and the "CDraw" 00039 library and any other such library that any version of Xara LX relased 00040 by Xara Group Ltd requires in order to compile and execute, including 00041 the static linking of that library to XaraLX. In the case of the 00042 "CDraw" library, you may satisfy obligation under the GNU General Public 00043 License to provide source code by providing a binary copy of the library 00044 concerned and a copy of the license accompanying it. 00045 00046 Nothing in this section restricts any of the rights you have under 00047 the GNU General Public License. 00048 00049 00050 SCOPE OF LICENSE 00051 ---------------- 00052 00053 This license applies to this program (XaraLX) and its constituent source 00054 files only, and does not necessarily apply to other Xara products which may 00055 in part share the same code base, and are subject to their own licensing 00056 terms. 00057 00058 This license does not apply to files in the wxXtra directory, which 00059 are built into a separate library, and are subject to the wxWindows 00060 license contained within that directory in the file "WXXTRA-LICENSE". 00061 00062 This license does not apply to the binary libraries (if any) within 00063 the "libs" directory, which are subject to a separate license contained 00064 within that directory in the file "LIBS-LICENSE". 00065 00066 00067 ARRANGEMENTS FOR CONTRIBUTION OF MODIFICATIONS 00068 ---------------------------------------------- 00069 00070 Subject to the terms of the GNU Public License (see above), you are 00071 free to do whatever you like with your modifications. However, you may 00072 (at your option) wish contribute them to Xara's source tree. You can 00073 find details of how to do this at: 00074 http://www.xaraxtreme.org/developers/ 00075 00076 Prior to contributing your modifications, you will need to complete our 00077 contributor agreement. This can be found at: 00078 http://www.xaraxtreme.org/developers/contribute/ 00079 00080 Please note that Xara will not accept modifications which modify any of 00081 the text between the start and end of this header (marked 00082 XARAHEADERSTART and XARAHEADEREND). 00083 00084 00085 MARKS 00086 ----- 00087 00088 Xara, Xara LX, Xara X, Xara X/Xtreme, Xara Xtreme, the Xtreme and Xara 00089 designs are registered or unregistered trademarks, design-marks, and/or 00090 service marks of Xara Group Ltd. All rights in these marks are reserved. 00091 00092 00093 Xara Group Ltd, Gaddesden Place, Hemel Hempstead, HP2 6EX, UK. 00094 http://www.xara.com/ 00095 00096 =================================XARAHEADEREND============================ 00097 */ 00098 00099 #include "camtypes.h" 00100 00101 //#include "ensure.h" - in camtypes.h [AUTOMATICALLY REMOVED] 00102 //#include "errors.h" - in camtypes.h [AUTOMATICALLY REMOVED] 00103 #include "camelot.h" 00104 //#include "andy.h" 00105 //#include "simon.h" // for _R(IDS_CONTINUE) 00106 //#include "errorbox.h" // for CInformErrorDialog::GetSafeParent 00107 00108 #ifdef AFX_DBG1_SEG 00109 #pragma code_seg(AFX_DBG1_SEG) 00110 #endif 00111 00112 // NOTE: in separate module so it can replaced if needed. 00113 #if 0 00114 #ifdef _DEBUG 00115 #undef THIS_FILE 00116 static char BASED_CODE THIS_FILE[] = __FILE__; 00117 #endif 00118 #endif 00119 00120 #ifdef _ENSURES 00121 INT32 AssertBusy = FALSE; // for testing diagnostics 00122 #endif 00123 00124 // Setup DEBUGBREAK macro 00125 #ifdef _DEBUG 00126 #ifdef __WXMSW__ 00127 #define DEBUGBREAK DebugBreak() 00128 #else 00129 #define DEBUGBREAK ::wxTrap() 00130 #endif 00131 #else 00132 #define DEBUGBREAK {} 00133 #endif 00134 00135 static void InternalAssert(const TCHAR * AssertDescription, const char * lpszFileName, INT32 nLine, BOOL UseMFC) 00136 { 00137 if (!UseMFC) 00138 #if defined(__WXMSW__) 00139 MessageBeep(MB_ICONASTERISK); 00140 #else 00141 ::wxBell(); 00142 #endif 00143 00144 00145 #ifdef _ENSURES 00146 00147 TCHAR sz[256]; 00148 static TCHAR BASED_CODE szTitle[] = wxT("Ensure Failed!"); 00149 00150 // In Unicode we need to convert the filename to TCHAR 00151 #if 0 != wxUSE_UNICODE 00152 TCHAR szRealFile[256]; 00153 size_t count = camMbstowcs(szRealFile, lpszFileName, 255); 00154 if (count == (size_t)-1) 00155 count = 0; 00156 szRealFile[count] = (TCHAR)0; 00157 const TCHAR* lpszRealFile = szRealFile; 00158 #else 00159 const TCHAR* lpszRealFile = lpszFileName; 00160 #endif 00161 00162 static TCHAR BASED_CODE szMessage[] = wxT("%s, File %s, Line %d"); 00163 static TCHAR BASED_CODE szMessageNoReason[] = wxT("Error %d@%s"); // note number first 00164 00165 // get app name or NULL if unknown (don't call assert) 00166 // const TCHAR *pszAppName = wxGetApp().GetAppName(); 00167 00168 if (AssertDescription != NULL) 00169 { 00170 camSnprintf(sz, 255, 00171 szMessage, 00172 AssertDescription, 00173 lpszRealFile, 00174 nLine); 00175 } 00176 else 00177 { 00178 camSnprintf(sz, 255, 00179 szMessageNoReason, 00180 nLine, 00181 lpszRealFile); 00182 } 00183 00184 #ifdef _DEBUG 00185 //PORTNOTE("other","Remove afxTraceEnabled") 00186 //#ifndef EXCLUDE_FROM_XARALX 00187 // if (afxTraceEnabled) 00188 #if defined(__WXMSW__) 00189 { 00190 // assume the debugger or auxiliary port 00191 #ifndef _MAC 00192 ::OutputDebugString(sz); 00193 ::OutputDebugString(_T(", ")); 00194 ::OutputDebugString(szTitle); 00195 ::OutputDebugString(_T("\n\r")); 00196 #else 00197 // Mac version needs them all together 00198 camStrcat(sz, _T(", ")); 00199 camStrcat(sz,szTitle); 00200 camStrcat(sz,_T("\n\r")); 00201 ::OutputDebugString(sz); 00202 #endif 00203 } 00204 #endif 00205 #endif 00206 00207 00208 if (AssertBusy > 0) 00209 { 00210 // getting assertion while inside an assertion 00211 // - it has already been traced, but 00212 // break into the debugger (or Dr Watson log) 00213 DEBUGBREAK; // else Win32s might die (just beeps) 00214 return; 00215 } 00216 00217 AssertBusy++; 00218 00219 if ( Error::IsInRenderThread() ) 00220 { 00221 TRACE( wxT("In RenderThread so clearing up system") ); 00222 Error::RenderThreadReset(); 00223 // Commented out - no problem using wx for render errors 00224 // UseMFC = FALSE; // mustn't use MFC for render errors 00225 } 00226 00227 INT32 result; 00228 00229 TCHAR RealErrorMsg[256]; 00230 00231 if (UseMFC) 00232 { 00233 // use our error handler to report ensures as it is more robust instead of MessageBox 00234 // The arrangement of buttons is the same as the exception handler dialog, not the same 00235 // as the original Ensure dialog (which was Abort/Retry/Ignore) 00236 ErrorInfo Info; 00237 00238 // try to preserve original error message 00239 camStrcpy( RealErrorMsg, Error::GetErrorString() ); 00240 00241 Error::SetErrorSerious( sz ); // set error msg (vaping any previous one) 00242 Info.ErrorMsg = 0; 00243 Info.Button[0] = _R(IDS_CONTINUE); 00244 Info.Button[1] = _R(IDS_QUIT); 00245 #ifndef EXCLUDE_FROM_XARALX 00246 if (IsWin32NT()) 00247 { 00248 #endif 00249 // only NT can cope with an Abort button 00250 Info.Button[2] = _R(IDS_ABORT); 00251 Info.Button[3] = _R(IDS_DEBUG); 00252 #ifndef EXCLUDE_FROM_XARALX 00253 } 00254 else 00255 { 00256 Info.Button[2] = _R(IDS_DEBUG); 00257 } 00258 #endif 00259 // no default button (or Help) 00260 Info.Cancel = 1; // Esc = Continue 00261 00262 result = InformGeneral( ERRORTYPE_ENSURE, &Info ); 00263 } 00264 else 00265 00266 { 00267 CamResource::DoneInit(); 00268 CCamApp::DisableSystem(); 00269 00270 // e.g. if this an MFC assert, don't use our lovely error handler becuase that itself 00271 // uses MFC. Instead we use good old MessageBox 00272 00273 #if !defined(EXCLUDE_FROM_RALPH) && !defined(EXCLUDE_FROM_XARALX) 00274 wxWindow *pParent = AfxGetApp().GetTopWindow(); 00275 PORTNOTE("other","Use CInformErrorDialog::GetSafeParent() when implemented") 00276 #ifndef EXCLUDE_FROM_XARALX 00277 CInformErrorDialog::GetSafeParent(); 00278 #endif 00279 #else 00280 wxWindow *pParent = NULL; 00281 #endif 00282 00283 wxMessageDialog Dialog( pParent, sz, szTitle, wxICON_HAND | wxYES_NO | wxCANCEL ); 00284 INT32 nCode = Dialog.ShowModal(); 00285 00286 CCamApp::EnableSystem(); 00287 00288 // convert MessageBox return value into a sane button ID 00289 switch (nCode) 00290 { 00291 case wxID_NO: 00292 result = _R(IDS_ABORT); 00293 break; 00294 case wxID_YES: 00295 result = _R(IDS_DEBUG); 00296 break; 00297 case wxID_CANCEL: 00298 default: 00299 result = _R(IDS_CONTINUE); 00300 break; 00301 } 00302 } 00303 00304 AssertBusy--; 00305 00306 if ((ResourceID)result == _R(IDS_DEBUG)) 00307 { 00308 DEBUGBREAK; 00309 } 00310 // no action on _R(IDS_CONTINUE)) 00311 else if ((ResourceID)result == _R(IDS_QUIT)) 00312 { 00313 // quit in a slightly nice way 00314 wxWindow *MainWnd = AfxGetApp().GetTopWindow(); 00315 if( MainWnd && MainWnd->IsShown() ) 00316 { 00317 MainWnd->Destroy(); 00318 } 00319 } // drop through 00320 if (((ResourceID)result == _R(IDS_ABORT)) || ((ResourceID)result == _R(IDS_QUIT))) 00321 { 00322 // if no window, try nasty exit 00323 AfxAbort(); 00324 return; // how did we get here? 00325 } 00326 00327 // if we ever get here we just carry on as if nothing happened 00328 00329 PORTNOTE("other","We can never use MFC again") 00330 #ifndef EXCLUDE_FROM_XARALX 00331 if (UseMFC) 00332 { 00333 if (RealErrorMsg[0]) 00334 Error::SetErrorSerious( RealErrorMsg ); // restore previous error msg 00335 else 00336 Error::ClearError(); 00337 } 00338 #endif 00339 #else 00340 // parameters not used if non-debug 00341 (void)lpszFileName; 00342 (void)nLine; 00343 #endif // _ENSURES 00344 00345 } 00346 00347 00348 /*********************************************************************************************** 00349 00350 > void EnsureFailedLine(LPCSTR AssertDescription, LPCSTR lpszFileName, INT32 nLine) 00351 00352 Author: Simon_Maneggio (Xara Group Ltd) <camelotdev@xara.com> 00353 Created: 3/5/93 00354 Inputs: AssertDescription: Reason for failure description 00355 lpszFileName: Filename of file that caused failure 00356 nLine: Line number that caused failure 00357 Outputs: - 00358 Returns: - 00359 Purpose: This function should only ever be invoked from the ENSURE macro 00360 which is similar to the ASSERT macro, the only difference being that 00361 it takes a parameter which describes the reason for the failure. 00362 Errors: - 00363 SeeAlso: - 00364 00365 ***********************************************************************************************/ 00366 /* Technical notes: 00367 00368 This function is an almost direct copy of the AfxAssertFailedLine function which is 00369 called from the ASSERT macro. 00370 */ 00371 00372 void EnsureFailedLine(const TCHAR * AssertDescription, const char * lpszFileName, INT32 nLine) 00373 { 00374 InternalAssert( AssertDescription, lpszFileName, nLine, TRUE ); 00375 } 00376 00377 /*********************************************************************************************** 00378 00379 > void AfxAssertLineFailed(LPCSTR lpszFileName, INT32 nLine) 00380 00381 Author: Alex_Bligh (Xara Group Ltd) <camelotdev@xara.com> 00382 Created: 28/2/94 00383 Inputs: lpszFileName: Filename of file that caused failure 00384 nLine: Line number that caused failure 00385 Outputs: - 00386 Returns: - 00387 Purpose: This is a more robust version than MFC provides. 00388 Errors: - 00389 SeeAlso: - 00390 00391 ***********************************************************************************************/ 00392 00393 #if COMPILER_REVISION >= 3 00394 // VC2 Beta 00395 BOOL AFXAPI AfxAssertFailedLine(LPCSTR lpszFileName, INT32 nLine) 00396 #else 00397 // VC1 or Chicago pre-Beta VC2 00398 void AFXAPI AfxAssertFailedLine(LPCSTR lpszFileName, INT32 nLine) 00399 #endif 00400 { 00401 #ifdef _MAC 00402 // ignore an incredibly annoying Mac assert which is something to do with rendering 00403 // the icons on our scroll bars 00404 if ( (nLine==119) && (camStrcmp(lpszFileName, "winbtn.cpp")==0) ) 00405 return FALSE; 00406 #endif 00407 00408 // must NOT use MFC for reporting this 00409 InternalAssert( _T("MFC Ensure"), lpszFileName, nLine, FALSE ); 00410 00411 #if COMPILER_REVISION >= 3 00412 return FALSE; 00413 #endif 00414 } 00415 00416 00417 00418