1#include <antlr/config.hpp>
13#include <antlr/TokenStream.hpp>
14#include <antlr/TokenWithIndex.hpp>
15#include <antlr/BitSet.hpp>
16#include <antlr/TokenStreamRewriteEngine.hpp>
18#ifdef ANTLR_CXX_SUPPORTS_NAMESPACE
22#ifndef NO_STATIC_CONSTS
23const size_t TokenStreamRewriteEngine::MIN_TOKEN_INDEX = 0;
24const int TokenStreamRewriteEngine::PROGRAM_INIT_SIZE = 100;
27const char* TokenStreamRewriteEngine::DEFAULT_PROGRAM_NAME =
"default";
31 struct compareOperationIndex {
32 typedef TokenStreamRewriteEngine::RewriteOperation RewriteOperation;
33 bool operator() (
const RewriteOperation* a,
const RewriteOperation* b )
const
35 return a->getIndex() < b->getIndex();
38 struct dumpTokenWithIndex {
39 dumpTokenWithIndex( ANTLR_USE_NAMESPACE(std)ostream& o ) : out(o) {}
40 void operator() (
const RefTokenWithIndex& t ) {
41 out <<
"[txt='" << t->getText() <<
"' tp=" << t->getType() <<
" idx=" << t->getIndex() <<
"]\n";
43 ANTLR_USE_NAMESPACE(std)ostream& out;
47TokenStreamRewriteEngine::TokenStreamRewriteEngine(TokenStream& upstream)
49, index(MIN_TOKEN_INDEX)
56TokenStreamRewriteEngine::TokenStreamRewriteEngine(TokenStream& upstream,
size_t initialSize )
58, index(MIN_TOKEN_INDEX)
65RefToken TokenStreamRewriteEngine::nextToken(
void )
70 t = RefTokenWithIndex(stream.nextToken());
74 if ( t->getType() != Token::EOF_TYPE ) {
79 }
while ( t && discardMask.member(t->getType()) );
83void TokenStreamRewriteEngine::rollback(
const std::string& programName,
84 size_t instructionIndex )
86 program_map::iterator rewrite = programs.find(programName);
87 if( rewrite != programs.end() )
89 operation_list& prog = rewrite->second;
90 operation_list::iterator
94 std::advance(j,instructionIndex);
100void TokenStreamRewriteEngine::originalToStream( std::ostream& out,
104 token_list::const_iterator s = tokens.begin();
105 std::advance( s, start );
106 token_list::const_iterator e = s;
107 std::advance( e, end-start );
108 std::for_each( s, e, tokenToStream(out) );
111void TokenStreamRewriteEngine::toStream( std::ostream& out,
112 const std::string& programName,
114 size_t lastToken )
const
116 if( tokens.size() == 0 )
119 program_map::const_iterator rewriter = programs.find(programName);
121 if ( rewriter == programs.end() )
125 const operation_list& prog = rewriter->second;
126 operation_list::const_iterator
127 rewriteOpIndex = prog.begin(),
128 rewriteOpEnd = prog.end();
130 size_t tokenCursor = firstToken;
132 if( lastToken > (tokens.size() - 1) )
133 lastToken = tokens.size() - 1;
135 while ( tokenCursor <= lastToken )
139 if( rewriteOpIndex != rewriteOpEnd )
141 size_t up_to_here = std::min(lastToken,(*rewriteOpIndex)->getIndex());
142 while( tokenCursor < up_to_here )
143 out << tokens[tokenCursor++]->getText();
145 while ( rewriteOpIndex != rewriteOpEnd &&
146 tokenCursor == (*rewriteOpIndex)->getIndex() &&
147 tokenCursor <= lastToken )
149 tokenCursor = (*rewriteOpIndex)->execute(out);
152 if( tokenCursor <= lastToken )
153 out << tokens[tokenCursor++]->getText();
157 std::for_each( rewriteOpIndex, rewriteOpEnd, executeOperation(out) );
158 rewriteOpIndex = rewriteOpEnd;
161void TokenStreamRewriteEngine::toDebugStream( std::ostream& out,
165 token_list::const_iterator s = tokens.begin();
166 std::advance( s, start );
167 token_list::const_iterator e = s;
168 std::advance( e, end-start );
169 std::for_each( s, e, dumpTokenWithIndex(out) );
172void TokenStreamRewriteEngine::addToSortedRewriteList(
const std::string& programName,
173 RewriteOperation* op )
175 program_map::iterator rewrites = programs.find(programName);
177 if ( rewrites == programs.end() )
182 programs.insert(std::make_pair(programName,ops));
185 operation_list& prog = rewrites->second;
193 operation_list::iterator i, end = prog.end();
197 if ( op->getIndex() >= (*i)->getIndex() ) {
205 operation_list::iterator pos = std::upper_bound( i, end, op, compareOperationIndex() );
212#ifdef ANTLR_CXX_SUPPORTS_NAMESPACE