예제 #1
0
int _registerSymbol(ParserTable& table, ident_t symbol, int new_id)
{
   int id = (int)table.defineSymbol(symbol);
   if (id == 0) {
      id = new_id;

      if ((symbol[0]<'A')||(symbol[0]>'Z'))
         id |= ParserTable::mskTerminal;

      table.registerSymbol(id, symbol);

      if (last_id < (id & ~mskAnySymbolMask)) last_id = id & ~mskAnySymbolMask;

      if (last_id >= mskTraceble) {
         printLine("WARNING: symbol id is overflown %d", last_id);
      }
   }
   return id;
}
예제 #2
0
TerminalInfo getTerminalInfo(ParserTable& table, LineInfo info)
{
   TerminalInfo terminal;
   terminal.value = info.line;
   terminal.col = info.column;
   terminal.row = info.row;
   terminal.disp = info.position;
   terminal.length = info.length;
   switch (info.state) {
      case dfaQuote:
         terminal.symbol = tsLiteral;
         break;
      case dfaCharacter:
         terminal.symbol = tsCharacter;
         break;
      case dfaEOF:
         terminal.symbol = tsEof;
         terminal.value = _eof_message;
         break;
      case dfaIdentifier:
         terminal.symbol = tsIdentifier;
         break;
	   case dfaFullIdentifier:
         terminal.symbol = tsReference;
         break;
	   case dfaPrivate:
         terminal.symbol = tsPrivate;
         break;
	   case dfaInteger:
         terminal.symbol = tsInteger;
         break;
      case dfaLong:
         terminal.symbol = tsLong;
         break;
	   case dfaHexInteger:
         terminal.symbol = tsHexInteger;
         break;
	   case dfaReal:
         terminal.symbol = tsReal;
         break;
      case dfaWideQuote:
         terminal.symbol = tsWide;
         break;
	   default:
         terminal.symbol = (Symbol)table.defineSymbol(terminal);
   }
   return terminal;
}
예제 #3
0
int main(int argc, char* argv[])
{
   printf("ELENA command line syntax generator %d.%d.%d (C)2005-2018 by Alexei Rakov\n", ENGINE_MAJOR_VERSION, ENGINE_MINOR_VERSION, BUILD_NUMBER);
   if (argc < 2 || argc > 3) {
      printLine("sg <syntax_file> [-cp<codepage>]");
      return 0;
   }
   try {
      int encoding = DEFAULT_ENCODING;

      if (argc==3) {
         ident_t arg = argv[2];

         if (arg.compare("-cp", 3)) {
            encoding = arg.toInt(3);
         }
         else {
            printLine("sg <syntax_file> [-cp<codepage>]");
            return 0;
         }
      }

      Path path(argv[1]);
      TextFileReader   sourceFile(path.c_str(), encoding, true);
      if (!sourceFile.isOpened()) {
         printLine("file not found %s", path);
      }

      TextSourceReader source(4, &sourceFile);
      ParserTable      table;
      LineInfo         info(0, 0, 0);
      IdentifierString token;
      int              rule[20];
      int              rule_len = 0;
      bool             arrayCheck = false;

      table.registerSymbol(ParserTable::nsEps, "eps");

      while (true) {
         info = source.read(token, IDENTIFIER_LEN);

         if (info.state == dfaEOF) break;

         if (token.compare("__define")) {
            source.read(token, IDENTIFIER_LEN);

            char number[10];
            source.read(number, 10);

            registerSymbol(table, token, ident_t(number).toInt());
         }
         else if (token.compare("->") && !arrayCheck) {
            if (rule_len > 2) {
               table.registerRule(rule[0], rule + 1, rule_len - 2);

               rule[0] = rule[rule_len - 1];
               rule_len = 1;
            }
            arrayCheck = true;
         }
         else if (token.compare("|") && rule_len != 1) {
            arrayCheck = false;
            table.registerRule(rule[0], rule + 1, rule_len - 1);

            rule_len = 1;
         }
         else {
            arrayCheck = false;
            rule[rule_len++] = registerSymbol(table, token, last_id + 1);
            if (token.compare("|"))
               source.read(token, IDENTIFIER_LEN);
         }
      }
      table.registerRule(rule[0], rule + 1, rule_len - 1);

      printLine("generating...\n");

      int ambigous = table.generate();
      if (ambigous) {
         printLine("error:ambigous rule %s\n", table.retrieveSymbol(ambigous));
         return -1;
      }

      printLine("saving...\n");

      path.changeExtension("dat");

      FileWriter file(path.c_str(), feRaw, false);
      table.save(&file);
   }
   catch(_ELENA_::InvalidChar& e) {
      printLine("(%d:%d): Invalid char %c\n", e.row, e.column, (char)e.ch);
   }
   return 0;
}