*/
#include "gendata.h"
+#include "ragel.h"
#include <iostream>
+/*
+ * Code generators.
+ */
+
+#include "cstable.h"
+#include "csftable.h"
+#include "csflat.h"
+#include "csfflat.h"
+#include "csgoto.h"
+#include "csfgoto.h"
+#include "csipgoto.h"
+#include "cssplit.h"
+
+#include "cdtable.h"
+#include "cdftable.h"
+#include "cdflat.h"
+#include "cdfflat.h"
+#include "cdgoto.h"
+#include "cdfgoto.h"
+#include "cdipgoto.h"
+#include "cdsplit.h"
+
+#include "dotcodegen.h"
+
+#include "javacodegen.h"
+
+#include "rubytable.h"
+#include "rubyftable.h"
+#include "rubyflat.h"
+#include "rubyfflat.h"
+#include "rbxgoto.h"
+
+string itoa( int i )
+{
+ char buf[16];
+ sprintf( buf, "%i", i );
+ return buf;
+}
+
+using std::cout;
using std::cerr;
using std::endl;
-CodeGenData *makeCodeGen( const char *sourceFileName, const char *fsmName,
- ostream &out, bool wantComplete )
+/* Invoked by the parser when a ragel definition is opened. */
+CodeGenData *dotMakeCodeGen( const char *sourceFileName, const char *fsmName, ostream &out )
+{
+ CodeGenData *codeGen = new GraphvizDotGen(out);
+
+ codeGen->sourceFileName = sourceFileName;
+ codeGen->fsmName = fsmName;
+
+ /* For normal code generation we want a transition on every character so we never
+ * end up in an undefined state. For graphviz this just clutters the
+ * drawing so we turn it off. */
+ codeGen->wantComplete = false;
+
+ return codeGen;
+}
+
+/* Invoked by the parser when a ragel definition is opened. */
+CodeGenData *cdMakeCodeGen( const char *sourceFileName, const char *fsmName, ostream &out )
+{
+ CodeGenData *codeGen = 0;
+ switch ( hostLang->lang ) {
+ case HostLang::C:
+ switch ( codeStyle ) {
+ case GenTables:
+ codeGen = new CTabCodeGen(out);
+ break;
+ case GenFTables:
+ codeGen = new CFTabCodeGen(out);
+ break;
+ case GenFlat:
+ codeGen = new CFlatCodeGen(out);
+ break;
+ case GenFFlat:
+ codeGen = new CFFlatCodeGen(out);
+ break;
+ case GenGoto:
+ codeGen = new CGotoCodeGen(out);
+ break;
+ case GenFGoto:
+ codeGen = new CFGotoCodeGen(out);
+ break;
+ case GenIpGoto:
+ codeGen = new CIpGotoCodeGen(out);
+ break;
+ case GenSplit:
+ codeGen = new CSplitCodeGen(out);
+ break;
+ }
+ break;
+
+ case HostLang::D:
+ switch ( codeStyle ) {
+ case GenTables:
+ codeGen = new DTabCodeGen(out);
+ break;
+ case GenFTables:
+ codeGen = new DFTabCodeGen(out);
+ break;
+ case GenFlat:
+ codeGen = new DFlatCodeGen(out);
+ break;
+ case GenFFlat:
+ codeGen = new DFFlatCodeGen(out);
+ break;
+ case GenGoto:
+ codeGen = new DGotoCodeGen(out);
+ break;
+ case GenFGoto:
+ codeGen = new DFGotoCodeGen(out);
+ break;
+ case GenIpGoto:
+ codeGen = new DIpGotoCodeGen(out);
+ break;
+ case GenSplit:
+ codeGen = new DSplitCodeGen(out);
+ break;
+ }
+ break;
+
+ default: break;
+ }
+
+ codeGen->sourceFileName = sourceFileName;
+ codeGen->fsmName = fsmName;
+
+ return codeGen;
+}
+
+/* Invoked by the parser when a ragel definition is opened. */
+CodeGenData *javaMakeCodeGen( const char *sourceFileName, const char *fsmName, ostream &out )
+{
+ CodeGenData *codeGen = new JavaTabCodeGen(out);
+
+ codeGen->sourceFileName = sourceFileName;
+ codeGen->fsmName = fsmName;
+
+ return codeGen;
+}
+
+/* Invoked by the parser when a ragel definition is opened. */
+CodeGenData *rubyMakeCodeGen( const char *sourceFileName, const char *fsmName, ostream &out )
+{
+ CodeGenData *codeGen = 0;
+ switch ( codeStyle ) {
+ case GenTables:
+ codeGen = new RubyTabCodeGen(out);
+ break;
+ case GenFTables:
+ codeGen = new RubyFTabCodeGen(out);
+ break;
+ case GenFlat:
+ codeGen = new RubyFlatCodeGen(out);
+ break;
+ case GenFFlat:
+ codeGen = new RubyFFlatCodeGen(out);
+ break;
+ case GenGoto:
+ if ( rubyImpl == Rubinius ) {
+ codeGen = new RbxGotoCodeGen(out);
+ } else {
+ cerr << "Goto style is still _very_ experimental "
+ "and only supported using Rubinius.\n"
+ "You may want to enable the --rbx flag "
+ " to give it a try.\n";
+ exit(1);
+ }
+ break;
+ default:
+ cout << "Invalid code style\n";
+ exit(1);
+ break;
+ }
+ codeGen->sourceFileName = sourceFileName;
+ codeGen->fsmName = fsmName;
+
+ return codeGen;
+}
+
+/* Invoked by the parser when a ragel definition is opened. */
+CodeGenData *csharpMakeCodeGen( const char *sourceFileName, const char *fsmName, ostream &out )
+{
+ CodeGenData *codeGen = 0;
+
+ switch ( codeStyle ) {
+ case GenTables:
+ codeGen = new CSharpTabCodeGen(out);
+ break;
+ case GenFTables:
+ codeGen = new CSharpFTabCodeGen(out);
+ break;
+ case GenFlat:
+ codeGen = new CSharpFlatCodeGen(out);
+ break;
+ case GenFFlat:
+ codeGen = new CSharpFFlatCodeGen(out);
+ break;
+ case GenGoto:
+ codeGen = new CSharpGotoCodeGen(out);
+ break;
+ case GenFGoto:
+ codeGen = new CSharpFGotoCodeGen(out);
+ break;
+ case GenIpGoto:
+ codeGen = new CSharpIpGotoCodeGen(out);
+ break;
+ case GenSplit:
+ codeGen = new CSharpSplitCodeGen(out);
+ break;
+ }
+
+ codeGen->sourceFileName = sourceFileName;
+ codeGen->fsmName = fsmName;
+
+ return codeGen;
+}
+
+
+CodeGenData *makeCodeGen( const char *sourceFileName, const char *fsmName, ostream &out )
{
CodeGenData *cgd = 0;
if ( generateDot )
- cgd = dotMakeCodeGen( sourceFileName, fsmName, out, wantComplete );
+ cgd = dotMakeCodeGen( sourceFileName, fsmName, out );
else if ( hostLang == &hostLangC )
- cgd = cdMakeCodeGen( sourceFileName, fsmName, out, wantComplete );
+ cgd = cdMakeCodeGen( sourceFileName, fsmName, out );
else if ( hostLang == &hostLangD )
- cgd = cdMakeCodeGen( sourceFileName, fsmName, out, wantComplete );
+ cgd = cdMakeCodeGen( sourceFileName, fsmName, out );
else if ( hostLang == &hostLangJava )
- cgd = javaMakeCodeGen( sourceFileName, fsmName, out, wantComplete );
+ cgd = javaMakeCodeGen( sourceFileName, fsmName, out );
else if ( hostLang == &hostLangRuby )
- cgd = rubyMakeCodeGen( sourceFileName, fsmName, out, wantComplete );
+ cgd = rubyMakeCodeGen( sourceFileName, fsmName, out );
else if ( hostLang == &hostLangCSharp )
- cgd = csharpMakeCodeGen( sourceFileName, fsmName, out, wantComplete );
+ cgd = csharpMakeCodeGen( sourceFileName, fsmName, out );
return cgd;
}
tokstartExpr(0),
tokendExpr(0),
dataExpr(0),
- wantComplete(0),
+ wantComplete(true),
hasLongestMatch(false),
noEnd(false),
noPrefix(false),
actionList.append( allActions+a );
}
-void CodeGenData::newAction( int anum, const char *name, int line,
- int col, GenInlineList *inlineList )
+void CodeGenData::newAction( int anum, const char *name,
+ const InputLoc &loc, GenInlineList *inlineList )
{
allActions[anum].actionId = anum;
allActions[anum].name = name;
- allActions[anum].loc.line = line;
- allActions[anum].loc.col = col;
+ allActions[anum].loc = loc;
allActions[anum].inlineList = inlineList;
}
* generators.
*
* Force a newline. */
- out << "\n";
+ out << '\n';
genLineDirective( out );
if ( strcmp( args[0], "data" ) == 0 ) {