Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028 #include "parser-debug.hpp"
00029 #include "parse_exception.hpp"
00030 #include "ValueParser.hpp"
00031 #include "../Attribute.hpp"
00032
00033 #include "../TaskContext.hpp"
00034 #include "../Service.hpp"
00035 #include "../types/GlobalsRepository.hpp"
00036
00037 #include <boost/bind.hpp>
00038 #include <boost/lexical_cast.hpp>
00039
00040 #include <iostream>
00041 using namespace std;
00042
00043 namespace RTT
00044 {
00045 using boost::bind;
00046 using namespace detail;
00047
00048 ValueParser::ValueParser( TaskContext* tc, CommonParser& cp)
00049 : commonparser(cp), peerparser(tc,cp), propparser(cp), context(tc)
00050 {
00051 BOOST_SPIRIT_DEBUG_RULE( constant );
00052 BOOST_SPIRIT_DEBUG_RULE( const_float );
00053 BOOST_SPIRIT_DEBUG_RULE( const_double );
00054 BOOST_SPIRIT_DEBUG_RULE( const_int );
00055 BOOST_SPIRIT_DEBUG_RULE( const_hex );
00056 BOOST_SPIRIT_DEBUG_RULE( const_uint );
00057 BOOST_SPIRIT_DEBUG_RULE( const_char );
00058 BOOST_SPIRIT_DEBUG_RULE( const_bool );
00059 BOOST_SPIRIT_DEBUG_RULE( const_string );
00060 BOOST_SPIRIT_DEBUG_RULE( named_constant );
00061
00062
00063
00064
00065 constant =
00066 const_float
00067 | const_double
00068 | const_hex
00069 | const_int
00070 | const_uint
00071 | const_bool
00072 | const_char
00073 | const_string
00074 | named_constant;
00075
00076 const_float =
00077 strict_real_p [
00078 boost::bind( &ValueParser::seenfloatconstant, this, _1 ) ] >> ch_p('f');
00079
00080 const_double =
00081 strict_real_p [
00082 boost::bind( &ValueParser::seendoubleconstant, this, _1 ) ];
00083
00084 const_hex = (str_p("0x") | str_p("0X")) >>
00085 hex_p [
00086 boost::bind( &ValueParser::seenhexconstant, this, _1 ) ];
00087
00088 const_int =
00089 int_p [
00090 boost::bind( &ValueParser::seenintconstant, this, _1 ) ];
00091
00092 const_uint =
00093 uint_p [
00094 boost::bind( &ValueParser::seenuintconstant, this, _1 ) ] >> ch_p('u');
00095
00096 const_bool =
00097 ( keyword_p( "true" ) | keyword_p("false") )[
00098 boost::bind( &ValueParser::seenboolconstant, this, _1, _2 ) ];
00099
00100 const_char = (ch_p('\'') >> ch_p('\\') >> ch_p('0') >> ch_p('\''))[boost::bind( &ValueParser::seennull,this)] |
00101 confix_p( "'", (c_escape_ch_p[ boost::bind( &ValueParser::seencharconstant, this, _1 ) ]) , "'" );
00102
00103 const_string = lexeme_d[confix_p(
00104 ch_p( '"' ), *c_escape_ch_p[ boost::bind( &ValueParser::push_str_char, this, _1 ) ], '"' )[ boost::bind( &ValueParser::seenstring, this ) ]];
00105
00106 named_constant =
00107 ( keyword_p("done")[boost::bind( &ValueParser::seennamedconstant, this, _1, _2 ) ]
00108 |
00109 ( peerparser.locator()[boost::bind( &ValueParser::seenpeer, this) ]
00110 >> propparser.locator()
00111 >> commonparser.identifier[boost::bind( &ValueParser::seennamedconstant, this, _1, _2 ) ]) )
00112 ;
00113 }
00114
00115 void ValueParser::seenpeer() {
00116
00117
00118
00119 propparser.setPropertyBag( peerparser.taskObject()->properties() );
00120 }
00121
00122 void ValueParser::seenboolconstant( iter_t begin, iter_t end )
00123 {
00124 std::string value( begin, end );
00125 assert( value == "true" || value == "false" );
00126 if ( value == "true" )
00127 ret =
00128 new ConstantDataSource<bool>( true );
00129 else
00130 ret =
00131 new ConstantDataSource<bool>( false );
00132 }
00133
00134 void ValueParser::seennamedconstant( iter_t begin, iter_t end )
00135 {
00136 std::string name( begin, end );
00137 Service::shared_ptr task = peerparser.taskObject();
00138 peerparser.reset();
00139
00140
00141
00142 if ( task && propparser.bag() && propparser.property() ) {
00143
00144 if ( ! propparser.bag()->find( name ) ) {
00145
00146 throw parse_exception_semantic_error("Property " + name + " not present in PropertyBag "+propparser.property()->getName()+" in "+ task->getName()+".");
00147 }
00148 ret = propparser.bag()->find( name )->getDataSource();
00149 propparser.reset();
00150 return;
00151 }
00152
00153
00154 if ( task && task->hasAttribute( name ) ) {
00155 ret = task->getValue(name)->getDataSource();
00156 return;
00157 }
00158 if ( task && task->hasProperty( name ) ) {
00159 ret = task->properties()->find(name)->getDataSource();
00160 return;
00161 }
00162
00163
00164 if ( GlobalsRepository::Instance()->hasAttribute( name ) ) {
00165 ret = GlobalsRepository::Instance()->getValue(name)->getDataSource();
00166 return;
00167 }
00168
00169 throw_(begin, "Value " + name + " not defined in "+ task->getName()+".");
00170 }
00171
00172 void ValueParser::seennull()
00173 {
00174 ret = new ConstantDataSource<char>( '\0' );
00175 }
00176
00177 void ValueParser::seencharconstant( iter_t c )
00178 {
00179 ret = new ConstantDataSource<char>( *c );
00180 }
00181
00182 void ValueParser::seenhexconstant( unsigned int i )
00183 {
00184 ret = new ConstantDataSource<unsigned int>( i );
00185 }
00186
00187 void ValueParser::seenintconstant( int i )
00188 {
00189 ret = new ConstantDataSource<int>( i );
00190 }
00191
00192 void ValueParser::seenuintconstant( unsigned int i )
00193 {
00194 ret = new ConstantDataSource<unsigned int>( i );
00195 }
00196
00197 void ValueParser::seenfloatconstant( double i )
00198 {
00199 ret = new ConstantDataSource<float>( float(i) );
00200 }
00201
00202 void ValueParser::seendoubleconstant( double i )
00203 {
00204 ret = new ConstantDataSource<double>( i );
00205 }
00206
00207 ValueParser::~ValueParser()
00208 {
00209 clear();
00210 }
00211
00212 void ValueParser::clear()
00213 {
00214 propparser.reset();
00215 }
00216
00217 rule_t& ValueParser::parser()
00218 {
00219 return constant;
00220 }
00221
00222 void ValueParser::push_str_char( char c )
00223 {
00224 mcurstring += c;
00225 }
00226
00227 void ValueParser::seenstring()
00228 {
00229
00230
00231
00232 mcurstring.erase( mcurstring.end() - 1 );
00233 ret = new ConstantDataSource<std::string>( mcurstring );
00234
00235 mcurstring.clear();
00236 }
00237 }