Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | File List | Class Members | File Members | Related Pages

Lexer.h

Go to the documentation of this file.
00001 #ifndef _Lexer_h_
00002 #define _Lexer_h_
00003 #include <ctype.h>
00004 #include <stdio.h>
00005 
00006 #include <iostream>
00007 #include <fstream>
00008 
00009 #include "Error.h"
00010 #include "readline.h"
00011 
00018 class Lexer {
00019         friend class SyntaxError;
00020       private:
00021         const char *_fn;
00022          std::ifstream _is;
00023 
00024         string _tok;
00025 
00026         string _buf;
00027         int _line;
00028         const char *_cbuf;
00029         const char *_cbufp;
00030       public:
00031          Lexer(const char *fn = NULL) {
00032                 _fn = NULL;
00033                 if (fn)
00034                         open(fn);
00035         } void close() {
00036                 if (!_fn)
00037                         return;
00038                 _fn = NULL;
00039                 _is.close();
00040         }
00041 
00042         void open(const char *fn) {
00043                 _is.open(fn);
00044                 if (!_is.good())
00045                         throw IOError("Stream bad", -1, ERROR_LOCATION);
00046                 _fn = fn;
00047                 _line = 0;
00048                 _buf = "";
00049                 _cbufp = _cbuf = _buf.c_str();
00050         }
00051 
00052         int eof() {
00053                 return _is.eof();
00054         }
00055 
00056         string curToken() {
00057                 return _tok;
00058         }
00059 
00060         string getToken() {
00061                 const char *q;
00062                 while (!(*_cbufp)) {
00063                         if (!_is.good())
00064                                 throw IOError("Stream bad", -1,
00065                                               ERROR_LOCATION);
00066                         _line++;
00067                         nlreadline(_is, _buf, 0);
00068                         if (_is.eof())
00069                                 return "";
00070                         if (!_is.good())
00071                                 throw IOError("Stream bad", -1,
00072                                               ERROR_LOCATION);
00073                         _cbufp = _cbuf = _buf.c_str();
00074                         while (isspace(*_cbufp))
00075                                 _cbufp++;
00076                         if (*_cbufp == '#')
00077                                 _cbufp = _cbuf + _buf.length();
00078                 }
00079                 q = _cbufp;
00080                 while (*q && !isspace(*q))
00081                         q++;
00082                 _tok.assign(_cbufp, q - _cbufp);
00083                 _cbufp = q;
00084                 while (isspace(*_cbufp))
00085                         _cbufp++;
00086                 return _tok;
00087         }
00088 
00089         void putbackToken(string token) {
00090                 _buf.replace(0, _cbufp - _cbuf, token + ' ');
00091                 _cbufp = _cbuf = _buf.c_str();
00092         }
00093 
00094         int isFlag(const string & token, const char *strg, int *flag) {
00095                 const char *ctok = token.c_str();
00096                 if (strcmp(ctok, strg) == 0) {
00097                         *flag = 1;
00098                         return 1;
00099                 }
00100                 if (strncmp(ctok, "not-", 4) == 0
00101                     && strcmp(ctok + 4, strg) == 0) {
00102                         *flag = 0;
00103                         return 1;
00104                 }
00105                 return 0;
00106         }
00107 };
00108 
00115 class SyntaxError:public Error {
00116       public:
00117         SyntaxError(const Lexer & lex, const char *txt, const char *file,
00118                     const char *function, int line)
00119         :Error(txt, file, function, line) {
00120                 char buf[256];
00121                  sprintf(buf, ":%d: ", lex._line);
00122 
00123                  _errtext = lex._fn;
00124                  _errtext += buf;
00125                  _errtext += txt;
00126                  VERB(slog.p(Logger::Error);
00127                       SyntaxError::print());
00128         } virtual void print() {
00129                 slog << "Exception!\n"
00130                     << "  Type: Syntax\n"
00131                     << "  Desc: " << _errtext << "\n";
00132         }
00133 };
00134 
00135 #endif

Generated on Sun Oct 24 21:08:17 2004 for NewsCache by doxygen 1.3.6-20040222