Limbo
3.5.4
Toggle main menu visibility
Loading...
Searching...
No Matches
limbo
parsers
tf
spirit
TfParser.h
Go to the documentation of this file.
1
7
8
#ifndef _TFPARSER_H
9
#define _TFPARSER_H
10
11
#include <iostream>
12
#include <fstream>
13
#include <sstream>
14
#include <vector>
15
#include <cassert>
16
#include <boost/array.hpp>
17
#include <boost/cstdint.hpp>
18
#include <boost/algorithm/string.hpp>
19
#include <boost/spirit/include/qi.hpp>
20
#include <boost/spirit/include/qi_no_case.hpp>
21
#include <boost/spirit/include/phoenix.hpp>
22
#include <boost/spirit/include/phoenix_bind.hpp>
23
#include <
limbo/parsers/tf/spirit/ErrorHandler.h
>
24
//#include "Gadget.h"
25
using
std::cout;
26
using
std::endl;
27
using
std::vector;
28
using
std::string;
29
using
std::ostringstream;
30
using
boost::int8_t;
31
using
boost::int32_t;
32
using
boost::int64_t;
33
using
boost::uint8_t;
34
using
boost::array;
35
36
namespace
qi = boost::spirit::qi;
37
namespace
ascii = boost::spirit::ascii;
38
namespace
spirit = boost::spirit;
39
namespace
phoenix = boost::phoenix;
40
42
#ifdef CASE_INSENSITIVE
43
#define TF_NO_CASE(X) no_case[X]
44
#else
45
#define TF_NO_CASE(X) X
46
#endif
47
52
struct
TfParser
53
{
61
struct
TfDataBase
62
{
63
// required callbacks
68
virtual
void
add_tf_layer_id
(
string
const
& s1, int32_t
const
& s2,
string
const
& s3) = 0;
69
};
70
75
template
<
typename
Iterator,
typename
Skipper,
typename
DataBaseType>
76
struct
TfGrammar
: qi::grammar<Iterator, Skipper>
77
{
78
qi::rule<Iterator, Skipper>
expression
;
79
qi::rule<Iterator, Skipper>
block_defn
;
80
qi::rule<Iterator, Skipper>
block_layer_id
;
81
qi::rule<Iterator, Skipper>
block_layer_purpose
;
82
qi::rule<Iterator, Skipper>
block_display
;
83
qi::rule<Iterator, string(), Skipper>
text
;
84
qi::rule<Iterator, string(), Skipper>
text_nc
;
85
86
DataBaseType&
m_db
;
87
91
TfGrammar
(DataBaseType& db,
ErrorHandler<Iterator>
& error_handler) :
TfGrammar
::base_type(
expression
),
m_db
(db)
92
{
93
using
qi::int_;
94
using
qi::uint_;
95
using
qi::double_;
96
using
qi::char_;
97
using
qi::_1;
98
using
qi::_2;
99
using
qi::_3;
100
using
qi::_4;
101
using
qi::_5;
102
using
qi::_a;
103
using
qi::lexeme;
104
using
qi::no_case;
105
using
spirit::repeat;
106
using
spirit::as_string;
107
using
spirit::lit;
108
using
spirit::inf;
109
110
expression
=
111
*
block_defn
112
;
113
block_defn
= lexeme[
TF_NO_CASE
(
"layerDefinitions"
)]
114
>> lit(
"("
)
115
>> *(
116
block_layer_id
117
|
block_layer_purpose
118
|
block_display
119
)
120
>> lit(
")"
)
121
;
122
block_layer_id
= lexeme[
TF_NO_CASE
(
"techLayers"
)]
123
>> lit(
"("
)
124
>> *(
125
(lit(
"("
) >>
text
>> int_ >>
text
> lit(
")"
)) [boost::phoenix::bind(&
TfGrammar::layer_id_cbk
,
this
, _1, _2, _3)]
126
)
127
>> lit(
")"
)
128
;
129
block_layer_purpose
= lexeme[
TF_NO_CASE
(
"techLayerPurposePriorities"
)]
130
>> lit(
"("
)
131
>> *(
132
(lit(
"("
) >>
text
>>
text
> lit(
")"
))
133
)
134
>> lit(
")"
)
135
;
136
block_display
= lexeme[
TF_NO_CASE
(
"techDisplays"
)]
137
>> lit(
"("
)
138
>> *(
139
(lit(
"("
) >>
text
>>
text
>>
text
>> repeat(5)[char_] > lit(
")"
))
140
)
141
>> lit(
")"
)
142
;
143
144
text
= lexeme[(char_(
"a-zA-Z"
) >> *char_(
"a-zA-Z_0-9-"
))];
145
text_nc
= lexeme[+char_(
"a-zA-Z_0-9.-"
)];
// text no constraints
146
148
#if (BOOST_VERSION/100)%1000 == 55
149
// following Error handler only works in boost 1.55.0
150
// and there will be compilation error for 1.56.0 and 1.57.0
151
// Error handling: on error in expr, call error_handler.
152
qi::on_error<qi::fail>(
expression
,
153
boost::phoenix::function<
ErrorHandler<Iterator>
>(error_handler)(
154
"Error! Expecting "
, _4, _3));
155
#else
156
qi::on_error<qi::fail>(
expression
,
157
phoenix::ref(std::cout)
158
<< phoenix::val(
"Error! Expecting "
)
159
<< _4
160
<<
" here: '"
161
<< phoenix::construct<string>(_3, _2)
162
<< phoenix::val(
"'\n"
)
163
);
164
#endif
165
}
166
171
void
layer_id_cbk
(
string
const
& s1, int32_t
const
& d2,
string
const
& s3)
172
{
173
m_db
.add_tf_layer_id(s1, d2, s3);
174
}
175
};
176
178
template
<
typename
Iterator>
179
struct
SkipperGrammar
: qi::grammar<Iterator>
180
{
181
qi::rule<Iterator>
skip
;
182
184
SkipperGrammar
() :
SkipperGrammar
::base_type(
skip
)
185
{
186
using
qi::char_;
187
using
qi::eol;
188
using
spirit::lit;
189
190
skip
= ascii::space
191
| (
";"
>> *(char_ - eol) >> eol )
192
;
193
}
194
};
195
198
template
<
typename
DataBaseType>
199
static
bool
read
(DataBaseType& db,
const
string
& tfFile)
200
{
201
std::ifstream in;
202
203
in.open(tfFile.c_str(), std::ios::in);
204
if
(!in.is_open())
205
{
206
cout <<
"Unable to open input file "
<< tfFile << endl;
207
return
false
;
208
}
209
210
in.unsetf(std::ios::skipws);
// No white space skipping!
211
string
str = std::string(std::istreambuf_iterator<char>(in.rdbuf()),
212
std::istreambuf_iterator<char>());
213
string::const_iterator iter = str.begin();
214
string::const_iterator end = str.end();
215
216
typedef
SkipperGrammar<string::const_iterator>
skip_type;
217
skip_type skip;
218
typedef
ErrorHandler<string::const_iterator>
error_handler_type;
219
error_handler_type error_handler (iter, end);
220
TfGrammar<string::const_iterator, skip_type, DataBaseType>
lg
(db, error_handler);
221
222
//TitleWriter().print("parsing tf file", 50, "#");
223
//bool r = qi::phrase_parse(iter, end, lg, boost::spirit::ascii::space);
224
bool
r = qi::phrase_parse(iter, end,
lg
, skip);
225
//TitleWriter().print((r && iter == end)? "parsing succeed" : "parsing failed", 50, "#");
226
227
return
r && iter == end;
228
}
229
};
230
231
#endif
ErrorHandler.h
error handler for Boost.Spirit parser
TF_NO_CASE
#define TF_NO_CASE(X)
an option to control case insensitivity
Definition
TfParser.h:45
limbo::geometry
namespace for Limbo.Geometry
Definition
Geometry.h:21
ErrorHandler
error handler
Definition
ErrorHandler.h:24
TfParser::SkipperGrammar
grammar of skipper
Definition
TfParser.h:180
TfParser::SkipperGrammar::SkipperGrammar
SkipperGrammar()
constructor
Definition
TfParser.h:184
TfParser::SkipperGrammar::skip
qi::rule< Iterator > skip
grammar to skip text
Definition
TfParser.h:181
TfParser::TfDataBase
Base class for tf database. Only pure virtual functions are defined. User needs to inheritate this ...
Definition
TfParser.h:62
TfParser::TfDataBase::add_tf_layer_id
virtual void add_tf_layer_id(string const &s1, int32_t const &s2, string const &s3)=0
add layer name, layer id, layer abbreviation
TfParser::TfGrammar
define grammar
Definition
TfParser.h:77
TfParser::TfGrammar::block_display
qi::rule< Iterator, Skipper > block_display
technology display
Definition
TfParser.h:82
TfParser::TfGrammar::expression
qi::rule< Iterator, Skipper > expression
expression
Definition
TfParser.h:78
TfParser::TfGrammar::block_layer_id
qi::rule< Iterator, Skipper > block_layer_id
layer id
Definition
TfParser.h:80
TfParser::TfGrammar::TfGrammar
TfGrammar(DataBaseType &db, ErrorHandler< Iterator > &error_handler)
constructor
Definition
TfParser.h:91
TfParser::TfGrammar::text_nc
qi::rule< Iterator, string(), Skipper > text_nc
no constraints
Definition
TfParser.h:84
TfParser::TfGrammar::block_defn
qi::rule< Iterator, Skipper > block_defn
layer definitions
Definition
TfParser.h:79
TfParser::TfGrammar::block_layer_purpose
qi::rule< Iterator, Skipper > block_layer_purpose
layer purpose
Definition
TfParser.h:81
TfParser::TfGrammar::layer_id_cbk
void layer_id_cbk(string const &s1, int32_t const &d2, string const &s3)
callback of layer id
Definition
TfParser.h:171
TfParser::TfGrammar::text
qi::rule< Iterator, string(), Skipper > text
text
Definition
TfParser.h:83
TfParser::TfGrammar::m_db
DataBaseType & m_db
reference to database
Definition
TfParser.h:86
TfParser
Tf parser for technology file.
Definition
TfParser.h:53
TfParser::read
static bool read(DataBaseType &db, const string &tfFile)
API to read tf file.
Definition
TfParser.h:199
Generated on
for Limbo by
1.17.0