Improved graphviz output and got -M and -S working again.
authorthurston <thurston@052ea7fc-9027-0410-9066-f65837a77df0>
Sun, 15 Mar 2009 22:55:19 +0000 (22:55 +0000)
committerthurston <thurston@052ea7fc-9027-0410-9066-f65837a77df0>
Sun, 15 Mar 2009 22:55:19 +0000 (22:55 +0000)
git-svn-id: http://svn.complang.org/ragel/trunk@741 052ea7fc-9027-0410-9066-f65837a77df0

ragel/dotcodegen.cpp
ragel/inputdata.cpp
ragel/inputdata.h
ragel/parsedata.h
ragel/rlparse.kl
ragel/rlscan.rl

index 4efcbab..dc401df 100644 (file)
@@ -314,13 +314,6 @@ void GraphvizDotGen::writeDotFile( )
 
 void GraphvizDotGen::finishRagelDef()
 {
-       if ( !graphvizDone ) {
-               graphvizDone = true;
-
-               /* For dot file generation we want to pick default transitions. */
-               redFsm->chooseDefaultSpan();
-
-               /* Write out with it. */
-               writeDotFile();
-       }
+       /* For dot file generation we want to pick default transitions. */
+       redFsm->chooseDefaultSpan();
 }
index 253e958..f2831e0 100644 (file)
 #include "parsedata.h"
 #include "rlparse.h"
 #include <iostream>
+#include "dotcodegen.h"
 
 using std::cout;
 using std::cerr;
 using std::endl;
 using std::ios;
 
-void InputData::generateSpecificReduced()
-{
-       if ( parserDict.length() > 0 ) {
-               /* There is either a machine spec or machine name given. */
-               ParseData *parseData = 0;
-               GraphDictEl *graphDictEl = 0;
-
-               /* Traverse the sections, break out when we find a section/machine
-                * that matches the one specified. */
-               for ( ParserDict::Iter parser = parserDict; parser.lte(); parser++ ) {
-                       ParseData *checkPd = parser->value->pd;
-                       if ( machineSpec == 0 || strcmp( checkPd->sectionName, machineSpec ) == 0 ) {
-                               GraphDictEl *checkGdEl = 0;
-                               if ( machineName == 0 || (checkGdEl = 
-                                               checkPd->graphDict.find( machineName )) != 0 )
-                               {
-                                       /* Have a machine spec and/or machine name that matches
-                                        * the -M/-S options. */
-                                       parseData = checkPd;
-                                       graphDictEl = checkGdEl;
-                                       break;
-                               }
-                       }
-               }
-
-               if ( parseData == 0 )
-                       error() << "could not locate machine specified with -S and/or -M" << endl;
-               else {
-                       /* Section/Machine to emit was found. Prepare and emit it. */
-                       parseData->prepareMachineGen( graphDictEl );
-                       if ( gblErrorCount == 0 )
-                               parseData->generateReduced( *this );
-               }
-       }
-
-       writeOutput();
-}
-
-
 /* Invoked by the parser when the root element is opened. */
 void InputData::cdDefaultFileName( const char *inputFile )
 {
@@ -175,36 +137,82 @@ void InputData::openOutput()
 
 void InputData::prepareMachineGen()
 {
-       /* No machine spec or machine name given. Generate everything. */
-       for ( ParserDict::Iter parser = parserDict; parser.lte(); parser++ ) {
-               ParseData *pd = parser->value->pd;
-               if ( pd->instanceList.length() > 0 )
-                       pd->prepareMachineGen( 0 );
+       if ( generateDot ) {
+               /* Locate a machine spec to generate dot output for. We can only emit.
+                * Dot takes one graph at a time. */
+               if ( machineSpec != 0 ) {
+                       /* Machine specified. */
+                       ParserDictEl *pdEl = parserDict.find( machineSpec );
+                       if ( pdEl == 0 )
+                               error() << "could not locate machine specified with -S and/or -M" << endp;
+                       dotGenParser = pdEl->value;
+               }
+               else { 
+                       /* No machine spec given, just use the first one. */
+                       if ( parserList.length() == 0 )
+                               error() << "no machine specification to generate graphviz output" << endp;
+
+                       dotGenParser = parserList.head;
+               }
+
+               GraphDictEl *gdEl = 0;
+
+               if ( machineName != 0 ) {
+                       gdEl = dotGenParser->pd->graphDict.find( machineName );
+                       if ( gdEl == 0 )
+                               error() << "machine definition/instantiation not found" << endp;
+               }
+               else {
+                       /* We are using the whole machine spec. Need to make sure there
+                        * are instances in the spec. */
+                       if ( dotGenParser->pd->instanceList.length() == 0 )
+                               error() << "no machine instantiations to generate graphviz output" << endp;
+               }
+
+               dotGenParser->pd->prepareMachineGen( gdEl );
+       }
+       else {
+               /* No machine spec or machine name given. Generate everything. */
+               for ( ParserDict::Iter parser = parserDict; parser.lte(); parser++ ) {
+                       ParseData *pd = parser->value->pd;
+                       if ( pd->instanceList.length() > 0 )
+                               pd->prepareMachineGen( 0 );
+               }
        }
 }
 
 void InputData::generateReduced()
 {
-       for ( ParserDict::Iter parser = parserDict; parser.lte(); parser++ ) {
-               ParseData *pd = parser->value->pd;
-               if ( pd->instanceList.length() > 0 )
-                       pd->generateReduced( *this );
+       if ( generateDot ) {
+               dotGenParser->pd->generateReduced( *this );
+       }
+       else {
+               for ( ParserDict::Iter parser = parserDict; parser.lte(); parser++ ) {
+                       ParseData *pd = parser->value->pd;
+                       if ( pd->instanceList.length() > 0 )
+                               pd->generateReduced( *this );
+               }
        }
 }
 
 void InputData::writeOutput()
 {
-       for ( InputItemList::Iter ii = inputItems; ii.lte(); ii++ ) {
-               if ( ii->type == InputItem::Write ) {
-                       CodeGenData *cgd = ii->pd->cgd;
-                       ::keyOps = &cgd->thisKeyOps;
+       if ( generateDot ) {
+               static_cast<GraphvizDotGen*>(dotGenParser->pd->cgd)->writeDotFile();
+       }
+       else {
+               for ( InputItemList::Iter ii = inputItems; ii.lte(); ii++ ) {
+                       if ( ii->type == InputItem::Write ) {
+                               CodeGenData *cgd = ii->pd->cgd;
+                               ::keyOps = &cgd->thisKeyOps;
 
-                       cgd->writeStatement( ii->loc, ii->writeArgs.length()-1, ii->writeArgs.data );
-               }
-               else /*if ( /!generateDot )*/ {
-                       *outStream << '\n';
-                       lineDirective( *outStream, inputFileName, ii->loc.line );
-                       *outStream << ii->data.str();
+                               cgd->writeStatement( ii->loc, ii->writeArgs.length()-1, ii->writeArgs.data );
+                       }
+                       else {
+                               *outStream << '\n';
+                               lineDirective( *outStream, inputFileName, ii->loc.line );
+                               *outStream << ii->data.str();
+                       }
                }
        }
 }
index caf1286..93550fa 100644 (file)
 
 #include "gendata.h"
 
+struct Parser;
+
 struct InputData
 {
        InputData( const char *inputFileName, bool outputActive, bool wantComplete ) : 
                inputFileName(inputFileName),
                outStream(0),
                outputActive(outputActive),
-               wantComplete(wantComplete)
+               wantComplete(wantComplete),
+               dotGenParser(0)
        {}
 
        /* The name of the root section, this does not change during an include. */
@@ -38,9 +41,9 @@ struct InputData
        ostream *outStream;
        bool outputActive;
        bool wantComplete;
+       Parser *dotGenParser;
 
        void writeOutput();
-       void generateSpecificReduced();
        void makeOutputStream();
        void openOutput();
        void generateReduced();
index 578b2a8..20ae599 100644 (file)
@@ -399,12 +399,15 @@ struct InputItem
 
 struct Parser;
 
-typedef AvlMap<char*, Parser *, CmpStr> ParserDict;
-typedef AvlMapEl<char*, Parser *> ParserDictEl;
+typedef AvlMap<const char*, Parser*, CmpStr> ParserDict;
+typedef AvlMapEl<const char*, Parser*> ParserDictEl;
+
+typedef DList<Parser> ParserList;
 
 typedef DList<InputItem> InputItemList;
 
 extern ParserDict parserDict;
+extern ParserList parserList;
 extern InputItemList inputItems;
 
 #endif
index c6731de..eb7f12d 100644 (file)
@@ -30,6 +30,7 @@ using std::cerr;
 using std::endl;
 
 ParserDict parserDict;
+ParserList parserList;
 InputItemList inputItems;
 
 %%{
index 58a5def..1c5e4bb 100644 (file)
@@ -284,6 +284,7 @@ void Scanner::handleMachine()
                        pdEl->value = new Parser( fileName, machine, sectionLoc );
                        pdEl->value->init();
                        parserDict.insert( pdEl );
+                       parserList.append( pdEl->value );
                }
 
                parser = pdEl->value;