00001
00002
00003
00004
00005
00006
00007 #include "logCtrl.h"
00008 #include "vexception.h"
00009
00010
00011 LogCtrl::LogCtrl(const char *fname, bool write)
00012 : mutex(SDL_CreateMutex()), logfile(fname), moduleTagTerminated(false),
00013 now_stream(""), now_line(0), line(""),
00014 fin(NULL), fd(NULL) {
00015 if (!logfile && write) {
00016 logfile = "/dev/null";
00017 }
00018
00019 lock();
00020 if (write) {
00021 fd = fopen(logfile, "w");
00022 } else {
00023 fin = new std::ifstream(logfile);
00024 }
00025 if ((write && !fd) || (!write && !*fin)) {
00026 perror("");
00027 std::string error_message = std::string("Couldn't open: ") + logfile;
00028 throw VMonitor_Exception(error_message.c_str());
00029 }
00030
00031 unlock();
00032 }
00033
00034
00035 LogCtrl::~LogCtrl(void) {
00036 flush();
00037 if (fd) {
00038 fclose(fd);
00039 }
00040 if (fin) {
00041 fin->close();
00042 }
00043 SDL_DestroyMutex(mutex);
00044 }
00045
00046
00047 void LogCtrl::lock(void) {
00048 SDL_LockMutex(mutex);
00049 }
00050
00051
00052 void LogCtrl::unlock(void) {
00053 SDL_UnlockMutex(mutex);
00054 }
00055
00056
00057 void LogCtrl::flush(void) {
00058 if (fd) {
00059 terminateModuleTag();
00060 fflush(fd);
00061 }
00062 }
00063
00064
00065 void LogCtrl::terminateModuleTag(void) {
00066 if (!moduleTagTerminated) {
00067 fprintf(fd, "</%s>\n", now_stream.c_str());
00068 now_stream = "";
00069 moduleTagTerminated = true;
00070 }
00071 }
00072
00073
00074 void LogCtrl::writeTag(const char *module,
00075 const char* command, unsigned long ticks) {
00076
00077 if (now_stream.compare(module)) {
00078 if (!now_stream.empty()) {
00079 terminateModuleTag();
00080 }
00081 now_stream.assign(module);
00082 fprintf(fd, "<%s>\n", module);
00083 moduleTagTerminated = false;
00084 }
00085 fprintf(fd, " <%s ticks=%ld", command, ticks);
00086 }
00087
00088
00089 void LogCtrl::writeTagEnd(void) {
00090 fprintf(fd, ">\n");
00091 }
00092
00093
00094 const char* LogCtrl::readLine(void) {
00095 ++now_line;
00096 getline(*fin, line);
00097 return line.c_str();
00098 }
00099
00100
00101 const char* LogCtrl::getLineBuffer(void) {
00102 return line.c_str();
00103 }
00104
00105
00106 void LogCtrl::readModuleTag(const char* line) {
00107 char module_tag[] = { '\0','\0','\0','\0','\0','\0','\0','\0','\0','\0' };
00108 sscanf(line, "<%s", module_tag);
00109 module_tag[strlen(module_tag) -1] = '\0';
00110 now_stream.assign(module_tag);
00111 }
00112
00113
00114 bool LogCtrl::checkModuleEnd(const char* line) {
00115 if ((strlen(line) > 2) && !strncmp("</", line, 2)) {
00116 return true;
00117 } else {
00118 return false;
00119 }
00120 }
00121
00122
00123 void LogCtrl::throwMissmathException(void) {
00124
00125 char *message = new char [80 + strlen(logfile)];
00126 if (fin->eof()) {
00127 sprintf(message, "%s:%d: Log data is terminated", logfile, now_line);
00128 } else {
00129 sprintf(message, "%s:%d: Missmatch log between program and data",
00130 logfile, now_line);
00131 }
00132 std::string error_message = message;
00133 delete [] message;
00134 throw VMonitor_Exception(error_message.c_str());
00135 }
00136
00137
00138 unsigned long LogCtrl::readTag(const char *module, const char* command) {
00139
00140 if (now_stream.empty()) {
00141 readModuleTag(readLine());
00142 }
00143
00144
00145 if (checkModuleEnd(readLine())) {
00146 now_stream.assign("");
00147 return readTag(module, command);
00148 } else {
00149
00150 if (now_stream.compare(module)) {
00151 fprintf(stderr, "expected: %s, actual: %s\n", module,now_stream.c_str());
00152 throwMissmathException();
00153 }
00154
00155 char command_buf[80];
00156 unsigned long ticks = 0;
00157 sscanf(line.c_str(), "%s ticks=%ld", command_buf, &ticks);
00158 char* command_name = &command_buf[1];
00159 if (strcmp(command, command_name)) {
00160 fprintf(stderr, "expected: %s, actual: %s\n", command, command_name);
00161 throwMissmathException();
00162 }
00163 return ticks;
00164 }
00165 }
00166