00001 // Copyright (C) 2001, Compaq Computer Corporation 00002 // 00003 // This file is part of Vesta. 00004 // 00005 // Vesta is free software; you can redistribute it and/or 00006 // modify it under the terms of the GNU Lesser General Public 00007 // License as published by the Free Software Foundation; either 00008 // version 2.1 of the License, or (at your option) any later version. 00009 // 00010 // Vesta is distributed in the hope that it will be useful, 00011 // but WITHOUT ANY WARRANTY; without even the implied warranty of 00012 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00013 // Lesser General Public License for more details. 00014 // 00015 // You should have received a copy of the GNU Lesser General Public 00016 // License along with Vesta; if not, write to the Free Software 00017 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 00018 00019 /* File: Err.C */ 00020 /* Last Modified On Mon May 23 23:21:06 EDT 2005 by ken@xorian.net */ 00021 /* Modified On Mon Apr 25 10:57:40 EDT 2005 by irina.furman@intel.com */ 00022 /* Modified On Wed Nov 22 21:08:51 PST 2000 by yuanyu */ 00023 /* Modified On Fri Jul 14 20:37:33 PDT 2000 by mann */ 00024 /* Modified On Fri Oct 31 10:27:40 PST 1997 by heydon */ 00025 /* Modified On Thu Jan 18 10:03:11 PST 1996 by horning */ 00026 /* Modified On Wed Dec 1 14:18:50 PST 1993 by hanna */ 00027 00028 #include <VestaSource.H> 00029 #include <ReposUI.H> 00030 #include "Err.H" 00031 #include "EvalBasics.H" 00032 #include "ValExpr.H" 00033 #include "Val.H" 00034 #include "Expr.H" 00035 #include "Location.H" 00036 #include "ThreadData.H" 00037 00038 using std::ostream; 00039 using std::cerr; 00040 using std::endl; 00041 00042 int errorCount; 00043 Basics::mutex outputMu; 00044 00045 void Error() { 00046 errorCount++; 00047 } 00048 00049 int ErrorCount() { 00050 return errorCount; 00051 } 00052 00053 void Error(const Text &msg, SrcLoc *loc) { 00054 errorCount++; 00055 if (loc != NULL && !loc->IsNone()) { 00056 cerr << loc->file << ", line " << loc->line << ", char " 00057 << loc->character << ":" << endl; 00058 } 00059 // Try to add a line break if "msg" contains "Current token class" 00060 int i = msg.FindText("Current token class"); 00061 ThreadData* td = NULL; 00062 if (i < 0) { 00063 if (maxThreads > 1 && (td = ThreadDataGet()) != NULL) { 00064 cerr << td->id << "/Error: " << msg; 00065 } 00066 else { 00067 cerr << "Error: " << msg; 00068 } 00069 } else { 00070 if (maxThreads > 1 && (td = ThreadDataGet()) != NULL) { 00071 cerr << td->id 00072 << "/Parse error: " << msg.Sub(0, i) << '\n' << msg.Sub(i); 00073 } 00074 else { 00075 cerr << "Parse error: " << msg.Sub(0, i) << '\n' << msg.Sub(i); 00076 } 00077 } 00078 } 00079 00080 void ErrorVal(const Val v) { 00081 v->PrintD(&cerr); 00082 } 00083 00084 void ErrorExpr(const Expr e) { 00085 e->PrintD(&cerr); 00086 } 00087 00088 void ErrorDetail(const Text &msg) { 00089 cerr << msg; 00090 } 00091 00092 void InternalError(const Text &procName) { 00093 errorCount++; 00094 cerr << "\nVesta evaluator: Internal error in procedure " 00095 << procName << "\n"; 00096 assert(false); 00097 } 00098 00099 void ErrorArgs(const Vals &args) { 00100 Vals work = args; 00101 00102 cerr << "("; 00103 while (!work.Null()) { 00104 work.Pop()->PrintD(&cerr); 00105 if (!work.Null()) 00106 cerr << ", "; 00107 } 00108 cerr << ")"; 00109 return; 00110 } 00111 00112 bool ErrorSummary(ostream *out) { 00113 if (errorCount == 0) { 00114 //*out << "\nNo errors were reported.\n"; 00115 return false; 00116 } 00117 if (errorCount == 1) 00118 *out << "\nOne error was reported.\n"; 00119 else 00120 *out << "\n" << errorCount << " errors were reported.\n"; 00121 out->flush(); 00122 return true; 00123 } 00124 00125 Val RecordErrorOnStack(Expr expr) { 00126 if (recordCallStack) { 00127 callStackMu.lock(); 00128 ThreadDataGet()->callStack->addlo(expr); 00129 callStackMu.unlock(); 00130 } 00131 Val result = NEW(ErrorVC); 00132 if (recordCallStack) { 00133 callStackMu.lock(); 00134 ThreadDataGet()->callStack->remlo(); 00135 callStackMu.unlock(); 00136 } 00137 return result; 00138 } 00139 00140 void ErrInit() { errorCount = 0; } 00141 00142 const Text VestaSourceErrorMsg(VestaSource::errorCode err) throw () 00143 { 00144 return ReposUI::errorCodeText(err); 00145 }