aboutsummaryrefslogtreecommitdiff
path: root/src/experimental/parser.h
diff options
context:
space:
mode:
Diffstat (limited to 'src/experimental/parser.h')
-rw-r--r--src/experimental/parser.h135
1 files changed, 135 insertions, 0 deletions
diff --git a/src/experimental/parser.h b/src/experimental/parser.h
new file mode 100644
index 0000000..a168c7b
--- /dev/null
+++ b/src/experimental/parser.h
@@ -0,0 +1,135 @@
1/*
2 * Copyright (C) 2007-2011 Xagasoft, All rights reserved.
3 *
4 * This file is part of the libbu++ library and is released under the
5 * terms of the license contained in the file LICENSE.
6 */
7
8#ifndef BU_PARSER_H
9#define BU_PARSER_H
10
11#include "bu/string.h"
12#include "bu/list.h"
13#include "bu/array.h"
14#include "bu/hash.h"
15#include "bu/signals.h"
16
17#include "bu/lexer.h"
18
19namespace Bu
20{
21 /**
22 * The base framework for a LR(1) grammar parser. Provided a proper set of
23 * ParserStates this will prase any input the lexer can provide.
24 */
25 class Parser
26 {
27 public:
28 Parser();
29 virtual ~Parser();
30
31 /**
32 * When a Lexer is pushed onto the stack it becomes the source for
33 * future tokens read by the parser until it is popped off the stack.
34 * The Parser takes ownership of every Lexer pushed onto the stack,
35 * and will delete it when it is popped off the stack.
36 */
37 void pushLexer( Lexer *pLex );
38
39 /**
40 * Pop a lexer off the stack, and delete it.
41 */
42 void popLexer();
43
44 Lexer::Token *popToken();
45 void pushToken( Lexer::Token *pTok );
46
47 /**
48 * Execute a parse.
49 */
50 void parse();
51
52 void setRootNonTerminal( int iRoot );
53 void setRootNonTerminal( const Bu::String &sRoot );
54
55 typedef Bu::Signal1<void, Parser &> Reduction;
56
57 /**
58 * Represents a possible state, either a terminal or non-terminal symbol
59 * in a Production.
60 */
61 class State
62 {
63 public:
64 enum Type
65 {
66 typeTerminal,
67 typeTerminalPush,
68 typeNonTerminal,
69 typeReduction
70 };
71
72 State( Type eType, int iIndex );
73 virtual ~State();
74
75 //private:
76 Type eType;
77 int iIndex;
78 };
79
80 typedef Bu::List<State> Production;
81
82 class NonTerminal
83 {
84 public:
85 NonTerminal();
86 virtual ~NonTerminal();
87
88 void addProduction( Production p );
89 void setCanSkip();
90
91// private:
92 typedef Bu::List<Production> ProductionList;
93 ProductionList lProduction;
94 bool bCanSkip;
95 };
96
97 int addNonTerminal( const Bu::String &sName, NonTerminal &nt );
98 int addNonTerminal( const Bu::String &sName );
99 void setNonTerminal( const Bu::String &sName, NonTerminal &nt );
100 int getNonTerminalId( const Bu::String &sName );
101 bool hasNonTerminal( const Bu::String &sName );
102
103 int addReduction( const Bu::String &sName, const Reduction &r );
104 int addReduction( const Bu::String &sName );
105 void setReduction( const Bu::String &sName, const Reduction &r );
106 int getReductionId( const Bu::String &sName );
107 bool hasReduction( const Bu::String &sName );
108
109 private:
110 bool selectProduction( int iNt, Lexer::Token *ptCur );
111 void advanceState();
112
113 private:
114 typedef Bu::List<Lexer *> LexerStack;
115 typedef Bu::List<Lexer::Token *> TokenStack;
116 typedef Bu::List<Production::const_iterator> StateStack;
117 typedef Bu::Array<Reduction> ReductionArray;
118 typedef Bu::Hash<Bu::String,int> NameIndexHash;
119 typedef Bu::Array<NonTerminal> NonTerminalArray;
120
121 LexerStack sLexer;
122 TokenStack sToken;
123 StateStack sState;
124 ReductionArray aReduction;
125 NameIndexHash hReductionName;
126 NonTerminalArray aNonTerminal;
127 NameIndexHash hNonTerminalName;
128 int iRootNonTerminal;
129 };
130Bu::Formatter &operator<<( Bu::Formatter &f, Bu::Parser::State::Type t );
131Bu::Formatter &operator<<( Bu::Formatter &f, const Bu::Parser::State &s );
132};
133
134
135#endif