Browse Source

A lot of work on PrismParser:

* Created a distinct parser for each expression type and for identifiers
* Removed all expression rules from PrismParser, using new parsers instead
* Reduced excessive usage of boost::lambda, using semantic actions only for single calls
* Moved actual state to new class (-> VariableState, whole two-run-logic can probably implemented there)
* Much cleanup

Work should be finished on expression parser, but not yet on prism parser...
main
gereon 12 years ago
parent
commit
b92260fed0
  1. 132
      src/parser/PrismParser.cpp
  2. 36
      src/parser/PrismParser.h
  3. 98
      src/parser/PrismParser/BaseGrammar.h
  4. 54
      src/parser/PrismParser/BooleanExpressionGrammar.cpp
  5. 35
      src/parser/PrismParser/BooleanExpressionGrammar.h
  6. 54
      src/parser/PrismParser/ConstBooleanExpressionGrammar.cpp
  7. 23
      src/parser/PrismParser/ConstBooleanExpressionGrammar.h
  8. 53
      src/parser/PrismParser/ConstDoubleExpressionGrammar.cpp
  9. 43
      src/parser/PrismParser/ConstDoubleExpressionGrammar.h
  10. 29
      src/parser/PrismParser/ConstIntegerExpressionGrammar.cpp
  11. 11
      src/parser/PrismParser/ConstIntegerExpressionGrammar.h
  12. 23
      src/parser/PrismParser/IdentifierGrammars.cpp
  13. 36
      src/parser/PrismParser/IdentifierGrammars.h
  14. 6
      src/parser/PrismParser/Includes.h
  15. 55
      src/parser/PrismParser/IntegerExpressionGrammar.cpp
  16. 28
      src/parser/PrismParser/IntegerExpressionGrammar.h
  17. 46
      src/parser/PrismParser/Tokens.h
  18. 90
      src/parser/PrismParser/VariableState.h

132
src/parser/PrismParser.cpp

@ -6,12 +6,15 @@
*/
#include "PrismParser.h"
#include "src/utility/OsDetection.h"
#include "src/parser/PrismParser/VariableState.h"
#include "src/parser/PrismParser/IntegerExpressionGrammar.h"
#include "src/parser/PrismParser/ConstIntegerExpressionGrammar.h"
#include "src/parser/PrismParser/BooleanExpressionGrammar.h"
#include "src/parser/PrismParser/ConstBooleanExpressionGrammar.h"
#include "src/parser/PrismParser/ConstDoubleExpressionGrammar.h"
#include "src/parser/PrismParser/ConstIntegerExpressionGrammar.h"
#include "src/parser/PrismParser/IntegerExpressionGrammar.h"
#include "src/parser/PrismParser/VariableState.h"
// If the parser fails due to ill-formed data, this exception is thrown.
#include "src/exceptions/WrongFileFormatException.h"
@ -40,72 +43,44 @@ namespace storm {
namespace parser {
PrismParser::PrismGrammar::PrismGrammar() : PrismParser::PrismGrammar::base_type(start) {
void dump(const std::string& s) {
std::cerr << "Dump: " << s << std::endl;
}
/*void dump(const std::string& s, ) {
std::cerr << "Dump: " << s << std::endl;
}*/
std::shared_ptr<BaseExpression> addIntegerConstant(const std::string& name, const std::shared_ptr<BaseExpression> value, std::shared_ptr<prism::VariableState> state) {
std::cerr << "addIntegerConstant: " << name << std::endl;
state->integerConstants_.add(name, value);
state->allConstantNames_.add(name, name);
return value;
}
this->state = std::shared_ptr<storm::parser::prism::VariableState>(new storm::parser::prism::VariableState());
storm::parser::prism::IntegerExpressionGrammar intExpr(this->state);
storm::parser::prism::ConstIntegerExpressionGrammar constIntExpr(this->state);
storm::parser::prism::BooleanExpressionGrammar boolExpr(this->state);
storm::parser::prism::ConstBooleanExpressionGrammar constBoolExpr(this->state);
PrismParser::PrismGrammar::PrismGrammar() : PrismParser::PrismGrammar::base_type(start), state(new storm::parser::prism::VariableState()) {
// This rule defines all identifiers that have not been previously used.
identifierName %= qi::as_string[qi::raw[qi::lexeme[((qi::alpha | qi::char_('_')) >> *(qi::alnum | qi::char_('_')))]]][ qi::_pass = phoenix::bind(&storm::parser::prism::VariableState::isIdentifier, this->state.get(), qi::_1) ];
identifierName %= qi::as_string[qi::raw[qi::lexeme[((qi::alpha | qi::char_('_')) >> *(qi::alnum | qi::char_('_')))]]][ qi::_pass = phoenix::bind(&storm::parser::prism::VariableState::isIdentifier, *this->state, qi::_1) ];
identifierName.name("identifier");
freeIdentifierName %= qi::as_string[qi::raw[qi::lexeme[((qi::alpha | qi::char_('_')) >> *(qi::alnum | qi::char_('_')))]]][ qi::_pass = phoenix::bind(&storm::parser::prism::VariableState::isFreeIdentifier, this->state.get(), qi::_1) ];
freeIdentifierName %= qi::as_string[qi::raw[qi::lexeme[((qi::alpha | qi::char_('_')) >> *(qi::alnum | qi::char_('_')))]]][ qi::_pass = phoenix::bind(&storm::parser::prism::VariableState::isFreeIdentifier, *this->state, qi::_1) ];
freeIdentifierName.name("unused identifier");
// This block defines all literal expressions.
booleanLiteralExpression = qi::bool_[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BooleanLiteral>(qi::_1))];
booleanLiteralExpression.name("boolean literal");
doubleLiteralExpression = qi::double_[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<DoubleLiteral>(qi::_1))];
doubleLiteralExpression.name("double literal");
// This block defines all expressions that are variables.
std::shared_ptr<BaseExpression> intvarexpr = std::shared_ptr<BaseExpression>(new VariableExpression(BaseExpression::int_, std::numeric_limits<uint_fast64_t>::max(), "int", std::shared_ptr<BaseExpression>(nullptr), std::shared_ptr<BaseExpression>(nullptr)));
std::shared_ptr<BaseExpression> boolvarexpr = std::shared_ptr<BaseExpression>(new VariableExpression(BaseExpression::bool_, std::numeric_limits<uint_fast64_t>::max(), "int", std::shared_ptr<BaseExpression>(nullptr), std::shared_ptr<BaseExpression>(nullptr)));
integerVariableExpression = identifierName[qi::_val = intvarexpr];
integerVariableExpression.name("integer variable");
booleanVariableExpression = identifierName[qi::_val = boolvarexpr];
booleanVariableExpression.name("boolean variable");
// This block defines all atomic expressions that are constant, i.e. literals and constants.
booleanConstantExpression %= (this->state->booleanConstants_ | booleanLiteralExpression);
booleanConstantExpression.name("boolean constant or literal");
doubleConstantExpression %= (this->state->doubleConstants_ | doubleLiteralExpression);
doubleConstantExpression.name("double constant or literal");
// This block defines all expressions of type double that are by syntax constant. That is, they are evaluable given the values for all constants.
constantAtomicDoubleExpression %= (qi::lit("(") >> constantDoubleExpression >> qi::lit(")") | doubleConstantExpression);
constantAtomicDoubleExpression.name("constant double expression");
constantDoubleMultExpression %= constantAtomicDoubleExpression[qi::_val = qi::_1] >> *((qi::lit("*")[qi::_a = true] | qi::lit("/")[qi::_a = false]) >> constantAtomicDoubleExpression)[phoenix::if_(qi::_a) [qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryNumericalFunctionExpression>(BaseExpression::double_, qi::_val, qi::_1, BinaryNumericalFunctionExpression::TIMES)) ] .else_ [qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryNumericalFunctionExpression>(BaseExpression::double_, qi::_val, qi::_1, BinaryNumericalFunctionExpression::DIVIDE))]];
constantDoubleMultExpression.name("constant double expression");
constantDoublePlusExpression %= constantDoubleMultExpression[qi::_val = qi::_1] >> *((qi::lit("+")[qi::_a = true] | qi::lit("-")[qi::_a = false]) >> constantDoubleMultExpression)[phoenix::if_(qi::_a) [qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryNumericalFunctionExpression>(BaseExpression::double_, qi::_val, qi::_1, BinaryNumericalFunctionExpression::PLUS)) ] .else_ [qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryNumericalFunctionExpression>(BaseExpression::double_, qi::_val, qi::_1, BinaryNumericalFunctionExpression::MINUS))]];
constantDoublePlusExpression.name("constant double expression");
constantDoubleExpression %= constantDoublePlusExpression;
constantDoubleExpression.name("constant double expression");
// This block defines all entities that are needed for parsing labels.
labelDefinition = (qi::lit("label") >> -qi::lit("\"") >> freeIdentifierName >> -qi::lit("\"") >> qi::lit("=") >> boolExpr >> qi::lit(";"))[phoenix::insert(qi::_r1, phoenix::construct<std::pair<std::string, std::shared_ptr<BaseExpression>>>(qi::_1, qi::_2)), phoenix::bind(this->state->labelNames_.add, qi::_1, qi::_1)];
labelDefinition = (qi::lit("label") >> -qi::lit("\"") >> freeIdentifierName >> -qi::lit("\"") >> qi::lit("=") >> prism::BooleanExpressionGrammar::instance(this->state) >> qi::lit(";"))[phoenix::insert(qi::_r1, phoenix::construct<std::pair<std::string, std::shared_ptr<BaseExpression>>>(qi::_1, qi::_2)), phoenix::bind(this->state->labelNames_.add, qi::_1, qi::_1)];
labelDefinition.name("label declaration");
labelDefinitionList %= *labelDefinition(qi::_r1);
labelDefinitionList.name("label declaration list");
// This block defines all entities that are needed for parsing a reward model.
stateRewardDefinition = (boolExpr > qi::lit(":") > constantDoubleExpression >> qi::lit(";"))[qi::_val = phoenix::construct<StateReward>(qi::_1, qi::_2)];
stateRewardDefinition = (prism::BooleanExpressionGrammar::instance(this->state) > qi::lit(":") > prism::ConstDoubleExpressionGrammar::instance(this->state) >> qi::lit(";"))[qi::_val = phoenix::construct<StateReward>(qi::_1, qi::_2)];
stateRewardDefinition.name("state reward definition");
transitionRewardDefinition = (qi::lit("[") > -(commandName[qi::_a = qi::_1]) > qi::lit("]") > boolExpr > qi::lit(":") > constantDoubleExpression > qi::lit(";"))[qi::_val = phoenix::construct<TransitionReward>(qi::_a, qi::_2, qi::_3)];
transitionRewardDefinition = (qi::lit("[") > -(commandName[qi::_a = qi::_1]) > qi::lit("]") > prism::BooleanExpressionGrammar::instance(this->state) > qi::lit(":") > prism::ConstDoubleExpressionGrammar::instance(this->state) > qi::lit(";"))[qi::_val = phoenix::construct<TransitionReward>(qi::_a, qi::_2, qi::_3)];
transitionRewardDefinition.name("transition reward definition");
rewardDefinition = (qi::lit("rewards") > qi::lit("\"") > freeIdentifierName > qi::lit("\"") > +(stateRewardDefinition[phoenix::push_back(qi::_a, qi::_1)] | transitionRewardDefinition[phoenix::push_back(qi::_b, qi::_1)]) >> qi::lit("endrewards"))[phoenix::insert(qi::_r1, phoenix::construct<std::pair<std::string, RewardModel>>(qi::_1, phoenix::construct<RewardModel>(qi::_1, qi::_a, qi::_b)))];
rewardDefinition.name("reward definition");
rewardDefinitionList = *rewardDefinition(qi::_r1);
rewardDefinitionList.name("reward definition list");
// This block defines auxiliary entities that are used to check whether a certain variable exist.
booleanVariableName %= this->state->booleanVariableNames_;
booleanVariableName.name("boolean variable");
integerVariableName %= this->state->integerVariableNames_;
integerVariableName.name("integer variable");
commandName %= this->state->commandNames_;
commandName.name("command name");
unassignedLocalBooleanVariableName %= this->state->localBooleanVariables_ - this->state->assignedLocalBooleanVariables_;
@ -114,19 +89,23 @@ PrismParser::PrismGrammar::PrismGrammar() : PrismParser::PrismGrammar::base_type
unassignedLocalIntegerVariableName.name("unassigned local integer variable");
// This block defines all entities that are needed for parsing a single command.
assignmentDefinition = (qi::lit("(") >> unassignedLocalIntegerVariableName > qi::lit("'") > qi::lit("=") > intExpr > qi::lit(")"))[phoenix::bind(this->state->assignedLocalIntegerVariables_.add, qi::_1, qi::_1), phoenix::insert(qi::_r2, phoenix::construct<std::pair<std::string, Assignment>>(qi::_1, phoenix::construct<Assignment>(qi::_1, qi::_2)))] | (qi::lit("(") > unassignedLocalBooleanVariableName > qi::lit("'") > qi::lit("=") > boolExpr > qi::lit(")"))[phoenix::bind(this->state->assignedLocalBooleanVariables_.add, qi::_1, qi::_1), phoenix::insert(qi::_r1, phoenix::construct<std::pair<std::string, Assignment>>(qi::_1, phoenix::construct<Assignment>(qi::_1, qi::_2)))];
assignmentDefinition = (qi::lit("(") >> unassignedLocalIntegerVariableName > qi::lit("'") > qi::lit("=") > prism::IntegerExpressionGrammar::instance(this->state) > qi::lit(")"))[phoenix::bind(this->state->assignedLocalIntegerVariables_.add, qi::_1, qi::_1), phoenix::insert(qi::_r2, phoenix::construct<std::pair<std::string, Assignment>>(qi::_1, phoenix::construct<Assignment>(qi::_1, qi::_2)))] | (qi::lit("(") > unassignedLocalBooleanVariableName > qi::lit("'") > qi::lit("=") > prism::BooleanExpressionGrammar::instance(this->state) > qi::lit(")"))[phoenix::bind(this->state->assignedLocalBooleanVariables_.add, qi::_1, qi::_1), phoenix::insert(qi::_r1, phoenix::construct<std::pair<std::string, Assignment>>(qi::_1, phoenix::construct<Assignment>(qi::_1, qi::_2)))];
assignmentDefinition.name("assignment");
assignmentDefinitionList = assignmentDefinition(qi::_r1, qi::_r2) % "&";
assignmentDefinitionList.name("assignment list");
updateDefinition = (constantDoubleExpression > qi::lit(":")[phoenix::clear(phoenix::ref(this->state->assignedLocalBooleanVariables_)), phoenix::clear(phoenix::ref(this->state->assignedLocalIntegerVariables_))] > assignmentDefinitionList(qi::_a, qi::_b))[qi::_val = phoenix::construct<Update>(qi::_1, qi::_a, qi::_b)];
updateDefinition = (prism::ConstDoubleExpressionGrammar::instance(this->state) > qi::lit(":")[phoenix::clear(phoenix::ref(this->state->assignedLocalBooleanVariables_)), phoenix::clear(phoenix::ref(this->state->assignedLocalIntegerVariables_))] > assignmentDefinitionList(qi::_a, qi::_b))[qi::_val = phoenix::construct<Update>(qi::_1, qi::_a, qi::_b)];
updateDefinition.name("update");
updateListDefinition = +updateDefinition % "+";
updateListDefinition.name("update list");
commandDefinition = (qi::lit("[") > -((freeIdentifierName[phoenix::bind(this->state->commandNames_.add, qi::_1, qi::_1)] | commandName)[qi::_a = qi::_1]) > qi::lit("]") > boolExpr > qi::lit("->") > updateListDefinition > qi::lit(";"))[qi::_val = phoenix::construct<Command>(qi::_a, qi::_2, qi::_3)];
commandDefinition = (
qi::lit("[") > -(
(freeIdentifierName[phoenix::bind(this->state->commandNames_.add, qi::_1, qi::_1)] | commandName)[qi::_a = qi::_1]
) > qi::lit("]") > prism::BooleanExpressionGrammar::instance(this->state) > qi::lit("->") > updateListDefinition > qi::lit(";")
)[qi::_val = phoenix::construct<Command>(qi::_a, qi::_2, qi::_3)];
commandDefinition.name("command");
// This block defines all entities that are needed for parsing variable definitions.
booleanVariableDefinition = (freeIdentifierName >> qi::lit(":") >> qi::lit("bool") > -(qi::lit("init") > constBoolExpr[qi::_b = phoenix::construct<std::shared_ptr<BaseExpression>>(qi::_1)]) > qi::lit(";"))
booleanVariableDefinition = (freeIdentifierName >> qi::lit(":") >> qi::lit("bool") > -(qi::lit("init") > prism::ConstBooleanExpressionGrammar::instance(this->state)[qi::_b = phoenix::construct<std::shared_ptr<BaseExpression>>(qi::_1)]) > qi::lit(";"))
[
//qi::_a = phoenix::bind(&VariableState<Iterator,Skipper>::addBooleanVariable, *this->state.get(), qi::_1),
qi::_a = phoenix::bind(&storm::parser::prism::VariableState::addBooleanVariable, *this->state, qi::_1, qi::_b),
@ -135,7 +114,10 @@ PrismParser::PrismGrammar::PrismGrammar() : PrismParser::PrismGrammar::base_type
phoenix::bind(this->state->localBooleanVariables_.add, qi::_1, qi::_1)
];
booleanVariableDefinition.name("boolean variable declaration");
integerVariableDefinition = (freeIdentifierName >> qi::lit(":") >> qi::lit("[") > constIntExpr > qi::lit("..") > constIntExpr > qi::lit("]") > -(qi::lit("init") > constIntExpr[qi::_b = phoenix::construct<std::shared_ptr<BaseExpression>>(qi::_1)]) > qi::lit(";"))
integerLiteralExpression = qi::int_[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<IntegerLiteral>(qi::_1))];
integerLiteralExpression.name("integer literal");
integerVariableDefinition = (freeIdentifierName >> qi::lit(":") >> qi::lit("[") > integerLiteralExpression > qi::lit("..") > integerLiteralExpression > qi::lit("]") > -(qi::lit("init") > prism::ConstIntegerExpressionGrammar::instance(this->state)[qi::_b = phoenix::construct<std::shared_ptr<BaseExpression>>(qi::_1)]) > qi::lit(";"))
[
qi::_a = phoenix::bind(&storm::parser::prism::VariableState::addIntegerVariable, *this->state, qi::_1, qi::_2, qi::_3, qi::_b),
phoenix::push_back(qi::_r1, phoenix::construct<IntegerVariable>(qi::_a, qi::_1, qi::_2, qi::_3, qi::_b)),
@ -148,7 +130,7 @@ PrismParser::PrismGrammar::PrismGrammar() : PrismParser::PrismGrammar::base_type
// This block defines all entities that are needed for parsing a module.
moduleDefinition = (qi::lit("module") >> freeIdentifierName
[phoenix::clear(phoenix::ref(this->state->localBooleanVariables_)), phoenix::clear(phoenix::ref(this->state->localIntegerVariables_))]
[phoenix::bind(&prism::VariableState::startModule, *this->state)]
>> *(variableDefinition(qi::_a, qi::_b, qi::_c, qi::_d)) >> +commandDefinition > qi::lit("endmodule"))
[
phoenix::bind(this->state->moduleNames_.add, qi::_1, qi::_1),
@ -172,14 +154,20 @@ PrismParser::PrismGrammar::PrismGrammar() : PrismParser::PrismGrammar::base_type
moduleDefinitionList %= +(moduleDefinition | moduleRenaming);
moduleDefinitionList.name("module list");
integerLiteralExpression = qi::int_[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<IntegerLiteral>(qi::_1))];
integerLiteralExpression.name("integer literal");
// This block defines all entities that are needed for parsing constant definitions.
definedBooleanConstantDefinition = (qi::lit("const") >> qi::lit("bool") >> freeIdentifierName >> qi::lit("=") > booleanLiteralExpression > qi::lit(";"))[phoenix::bind(this->state->booleanConstants_.add, qi::_1, qi::_2), phoenix::bind(this->state->allConstantNames_.add, qi::_1, qi::_1), qi::_val = qi::_2];
definedBooleanConstantDefinition = (qi::lit("const") >> qi::lit("bool") >> freeIdentifierName >> qi::lit("=") > prism::ConstBooleanExpressionGrammar::instance(this->state) > qi::lit(";"))[phoenix::bind(this->state->booleanConstants_.add, qi::_1, qi::_2), phoenix::bind(this->state->allConstantNames_.add, qi::_1, qi::_1), qi::_val = qi::_2];
definedBooleanConstantDefinition.name("defined boolean constant declaration");
definedIntegerConstantDefinition = (qi::lit("const") >> qi::lit("int") >> freeIdentifierName >> qi::lit("=") > integerLiteralExpression > qi::lit(";"))[phoenix::bind(this->state->integerConstants_.add, qi::_1, qi::_2), phoenix::bind(this->state->allConstantNames_.add, qi::_1, qi::_1), qi::_val = qi::_2];
definedIntegerConstantDefinition = (
qi::lit("const") >>
qi::lit("int")[phoenix::bind(&dump, "const int")] >>
freeIdentifierName >>
qi::lit("=")[phoenix::bind(&dump, "const int <ident> = ")] >>
//constIntExpr.integerLiteralExpression[phoenix::bind(&dump, "const int <ident> = <value>")] >>
prism::ConstIntegerExpressionGrammar::instance(this->state)[phoenix::bind(&dump, "const int <ident> = <value>")] >>
qi::lit(";")[phoenix::bind(&dump, "const int <ident> = <value>;")]
)[ qi::_val = phoenix::bind(&addIntegerConstant, qi::_1, qi::_2, this->state) ];
definedIntegerConstantDefinition.name("defined integer constant declaration");
definedDoubleConstantDefinition = (qi::lit("const") >> qi::lit("double") >> freeIdentifierName >> qi::lit("=") > doubleLiteralExpression > qi::lit(";"))[phoenix::bind(this->state->doubleConstants_.add, qi::_1, qi::_2), phoenix::bind(this->state->allConstantNames_.add, qi::_1, qi::_1), qi::_val = qi::_2];
definedDoubleConstantDefinition = (qi::lit("const") >> qi::lit("double") >> freeIdentifierName >> qi::lit("=") > prism::ConstDoubleExpressionGrammar::instance(this->state) > qi::lit(";"))[phoenix::bind(this->state->doubleConstants_.add, qi::_1, qi::_2), phoenix::bind(this->state->allConstantNames_.add, qi::_1, qi::_1), qi::_val = qi::_2];
definedDoubleConstantDefinition.name("defined double constant declaration");
undefinedBooleanConstantDefinition = (qi::lit("const") >> qi::lit("bool") > freeIdentifierName > qi::lit(";"))[qi::_a = phoenix::construct<std::shared_ptr<BooleanConstantExpression>>(phoenix::new_<BooleanConstantExpression>(qi::_1)), phoenix::insert(qi::_r1, phoenix::construct<std::pair<std::string, std::shared_ptr<BooleanConstantExpression>>>(qi::_1, qi::_a)), phoenix::bind(this->state->booleanConstants_.add, qi::_1, qi::_a), phoenix::bind(this->state->allConstantNames_.add, qi::_1, qi::_1)];
undefinedBooleanConstantDefinition.name("undefined boolean constant declaration");
@ -187,32 +175,28 @@ PrismParser::PrismGrammar::PrismGrammar() : PrismParser::PrismGrammar::base_type
undefinedIntegerConstantDefinition.name("undefined integer constant declaration");
undefinedDoubleConstantDefinition = (qi::lit("const") >> qi::lit("double") > freeIdentifierName > qi::lit(";"))[qi::_a = phoenix::construct<std::shared_ptr<DoubleConstantExpression>>(phoenix::new_<DoubleConstantExpression>(qi::_1)), phoenix::insert(qi::_r1, phoenix::construct<std::pair<std::string, std::shared_ptr<DoubleConstantExpression>>>(qi::_1, qi::_a)), phoenix::bind(this->state->doubleConstants_.add, qi::_1, qi::_a), phoenix::bind(this->state->allConstantNames_.add, qi::_1, qi::_1)];
undefinedDoubleConstantDefinition.name("undefined double constant declaration");
definedConstantDefinition %= (definedBooleanConstantDefinition | definedIntegerConstantDefinition | definedDoubleConstantDefinition);
definedConstantDefinition %= (definedBooleanConstantDefinition[phoenix::bind(&dump, "<defBoolConst>")] | definedIntegerConstantDefinition[phoenix::bind(&dump, "<defIntConst>")] | definedDoubleConstantDefinition[phoenix::bind(&dump, "<defDoubleConst>")]);
definedConstantDefinition.name("defined constant declaration");
undefinedConstantDefinition = (undefinedBooleanConstantDefinition(qi::_r1) | undefinedIntegerConstantDefinition(qi::_r2) | undefinedDoubleConstantDefinition(qi::_r3));
undefinedConstantDefinition.name("undefined constant declaration");
constantDefinitionList = *(definedConstantDefinition | undefinedConstantDefinition(qi::_r1, qi::_r2, qi::_r3));
constantDefinitionList = *(definedConstantDefinition[phoenix::bind(&dump, "<defConst>")] | undefinedConstantDefinition(qi::_r1, qi::_r2, qi::_r3)[phoenix::bind(&dump, "<undefConst>")]);
constantDefinitionList.name("constant declaration list");
// This block defines all entities that are needed for parsing a program.
modelTypeDefinition = modelType_;
modelTypeDefinition.name("model type");
start = (modelTypeDefinition > constantDefinitionList(qi::_a, qi::_b, qi::_c) > moduleDefinitionList > rewardDefinitionList(qi::_d) > labelDefinitionList(qi::_e))[qi::_val = phoenix::construct<Program>(qi::_1, qi::_a, qi::_b, qi::_c, qi::_2, qi::_d, qi::_e)];
start = (
modelTypeDefinition[phoenix::bind(&dump, "<model type>")] >
constantDefinitionList(qi::_a, qi::_b, qi::_c)[phoenix::bind(&dump, "<constants>")] >
moduleDefinitionList[phoenix::bind(&dump, "<modules>")] >
rewardDefinitionList(qi::_d)[phoenix::bind(&dump, "<rewards>")] >
labelDefinitionList(qi::_e)[phoenix::bind(&dump, "<labels>")]
)[qi::_val = phoenix::construct<Program>(qi::_1, qi::_a, qi::_b, qi::_c, qi::_2, qi::_d, qi::_e)];
start.name("probabilistic program declaration");
}
void PrismParser::PrismGrammar::prepareForSecondRun() {
// Clear constants.
storm::parser::prism::IntegerExpressionGrammar intExpr(this->state);
storm::parser::prism::ConstIntegerExpressionGrammar constIntExpr(this->state);
this->state->prepareForSecondRun();
// Override variable expressions: only allow declared variables.
integerVariableExpression %= this->state->integerVariables_;
integerVariableExpression.name("integer variable");
booleanVariableExpression %= this->state->booleanVariables_;
booleanVariableExpression.name("boolean variable");
}
/*!

36
src/parser/PrismParser.h

@ -11,8 +11,14 @@
// All classes of the intermediate representation are used.
#include "src/ir/IR.h"
#include "src/parser/PrismParser/Includes.h"
#include "src/parser/PrismParser/UtilityGrammars.h"
#include "src/parser/PrismParser/Tokens.h"
#include "src/parser/PrismParser/IdentifierGrammars.h"
#include "src/parser/PrismParser/VariableState.h"
#include "src/parser/PrismParser/ConstBooleanExpressionGrammar.h"
#include "src/parser/PrismParser/ConstDoubleExpressionGrammar.h"
#include "src/parser/PrismParser/ConstIntegerExpressionGrammar.h"
#include "src/parser/PrismParser/BooleanExpressionGrammar.h"
#include "src/parser/PrismParser/IntegerExpressionGrammar.h"
// Used for file input.
#include <istream>
@ -62,6 +68,7 @@ public:
qi::rule<Iterator, Module(), qi::locals<std::map<std::string, std::string>>, Skipper> moduleRenaming;
// Rules for variable definitions.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> integerLiteralExpression;
qi::rule<Iterator, qi::unused_type(std::vector<BooleanVariable>&, std::vector<IntegerVariable>&, std::map<std::string, uint_fast64_t>&, std::map<std::string, uint_fast64_t>&), Skipper> variableDefinition;
qi::rule<Iterator, qi::unused_type(std::vector<BooleanVariable>&, std::map<std::string, uint_fast64_t>&), qi::locals<uint_fast64_t, std::shared_ptr<BaseExpression>>, Skipper> booleanVariableDefinition;
qi::rule<Iterator, qi::unused_type(std::vector<IntegerVariable>&, std::map<std::string, uint_fast64_t>&), qi::locals<uint_fast64_t, std::shared_ptr<BaseExpression>>, Skipper> integerVariableDefinition;
@ -74,8 +81,6 @@ public:
qi::rule<Iterator, qi::unused_type(std::map<std::string, Assignment>&, std::map<std::string, Assignment>&), Skipper> assignmentDefinition;
// Rules for variable/command names.
qi::rule<Iterator, std::string(), Skipper> integerVariableName;
qi::rule<Iterator, std::string(), Skipper> booleanVariableName;
qi::rule<Iterator, std::string(), Skipper> commandName;
qi::rule<Iterator, std::string(), Skipper> unassignedLocalBooleanVariableName;
qi::rule<Iterator, std::string(), Skipper> unassignedLocalIntegerVariableName;
@ -91,7 +96,6 @@ public:
qi::rule<Iterator, qi::unused_type(std::map<std::string, std::shared_ptr<BaseExpression>>&), Skipper> labelDefinition;
// Rules for constant definitions.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> integerLiteralExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantDefinition;
qi::rule<Iterator, qi::unused_type(std::map<std::string, std::shared_ptr<BooleanConstantExpression>>&, std::map<std::string, std::shared_ptr<IntegerConstantExpression>>&, std::map<std::string, std::shared_ptr<DoubleConstantExpression>>&), Skipper> undefinedConstantDefinition;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> definedConstantDefinition;
@ -102,34 +106,14 @@ public:
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> definedIntegerConstantDefinition;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> definedDoubleConstantDefinition;
qi::rule<Iterator, std::string(), Skipper> freeIdentifierName;
qi::rule<Iterator, std::string(), Skipper> identifierName;
qi::rule<Iterator, std::string(), Skipper, Skipper2> freeIdentifierName;
qi::rule<Iterator, std::string(), Skipper, Skipper2> identifierName;
// The starting point for arbitrary expressions.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> expression;
// Rules with double result type.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantDoubleExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), qi::locals<bool>, Skipper> constantDoublePlusExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), qi::locals<bool>, Skipper> constantDoubleMultExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantAtomicDoubleExpression;
// Rules for variable recognition.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> booleanVariableExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> booleanVariableCreatorExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> integerVariableExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), qi::locals<std::shared_ptr<BaseExpression>>, Skipper> integerVariableCreatorExpression;
// Rules for constant recognition.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> booleanConstantExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> integerConstantExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> doubleConstantExpression;
// Rules for literal recognition.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> literalExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> booleanLiteralExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> doubleLiteralExpression;
storm::parser::prism::keywordsStruct keywords_;
storm::parser::prism::modelTypeStruct modelType_;
storm::parser::prism::relationalOperatorStruct relations_;

98
src/parser/PrismParser/BaseGrammar.h

@ -0,0 +1,98 @@
/*
* File: Keywords.h
* Author: nafur
*
* Created on April 10, 2013, 6:03 PM
*/
#ifndef BASEGRAMMAR_H
#define BASEGRAMMAR_H
#include "Includes.h"
#include "VariableState.h"
namespace storm {
namespace parser {
namespace prism {
template <typename T>
class BaseGrammar {
public:
BaseGrammar(std::shared_ptr<VariableState>& state) : state(state) {}
static T& instance(std::shared_ptr<VariableState>& state = nullptr) {
if (BaseGrammar::instanceObject == nullptr) {
BaseGrammar::instanceObject = std::shared_ptr<T>(new T(state));
}
return *BaseGrammar::instanceObject;
}
std::shared_ptr<BaseExpression> createBoolLiteral(const bool value) {
return std::shared_ptr<BooleanLiteral>(new BooleanLiteral(value));
}
std::shared_ptr<BaseExpression> createDoubleLiteral(const double value) {
return std::shared_ptr<DoubleLiteral>(new DoubleLiteral(value));
}
std::shared_ptr<BaseExpression> createIntLiteral(const int_fast64_t value) {
return std::shared_ptr<IntegerLiteral>(new IntegerLiteral(value));
}
std::shared_ptr<BaseExpression> createPlus(const std::shared_ptr<BaseExpression> left, bool addition, const std::shared_ptr<BaseExpression> right, BaseExpression::ReturnType type) {
if (addition) {
return std::shared_ptr<BinaryNumericalFunctionExpression>(new BinaryNumericalFunctionExpression(type, left, right, BinaryNumericalFunctionExpression::PLUS));
} else {
return std::shared_ptr<BinaryNumericalFunctionExpression>(new BinaryNumericalFunctionExpression(type, left, right, BinaryNumericalFunctionExpression::MINUS));
}
}
std::shared_ptr<BaseExpression> createDoublePlus(const std::shared_ptr<BaseExpression> left, bool addition, const std::shared_ptr<BaseExpression> right) {
return this->createPlus(left, addition, right, BaseExpression::double_);
}
std::shared_ptr<BaseExpression> createIntPlus(const std::shared_ptr<BaseExpression> left, bool addition, const std::shared_ptr<BaseExpression> right) {
return this->createPlus(left, addition, right, BaseExpression::int_);
}
std::shared_ptr<BaseExpression> createIntMult(const std::shared_ptr<BaseExpression> left, const std::shared_ptr<BaseExpression> right) {
return std::shared_ptr<BinaryNumericalFunctionExpression>(new BinaryNumericalFunctionExpression(BaseExpression::int_, left, right, BinaryNumericalFunctionExpression::TIMES));
}
std::shared_ptr<BaseExpression> createDoubleMult(const std::shared_ptr<BaseExpression> left, bool multiplication, const std::shared_ptr<BaseExpression> right) {
if (multiplication) {
return std::shared_ptr<BinaryNumericalFunctionExpression>(new BinaryNumericalFunctionExpression(BaseExpression::double_, left, right, BinaryNumericalFunctionExpression::TIMES));
} else {
return std::shared_ptr<BinaryNumericalFunctionExpression>(new BinaryNumericalFunctionExpression(BaseExpression::double_, left, right, BinaryNumericalFunctionExpression::DIVIDE));
}
}
std::shared_ptr<BaseExpression> createRelation(std::shared_ptr<BaseExpression> left, BinaryRelationExpression::RelationType relationType, std::shared_ptr<BaseExpression> right) {
return std::shared_ptr<BinaryRelationExpression>(new BinaryRelationExpression(left, right, relationType));
}
std::shared_ptr<BaseExpression> createNot(std::shared_ptr<BaseExpression> child) {
return std::shared_ptr<UnaryBooleanFunctionExpression>(new UnaryBooleanFunctionExpression(child, UnaryBooleanFunctionExpression::NOT));
}
std::shared_ptr<BaseExpression> createAnd(std::shared_ptr<BaseExpression> left, std::shared_ptr<BaseExpression> right) {
return std::shared_ptr<BinaryBooleanFunctionExpression>(new BinaryBooleanFunctionExpression(left, right, BinaryBooleanFunctionExpression::AND));
}
std::shared_ptr<BaseExpression> createOr(std::shared_ptr<BaseExpression> left, std::shared_ptr<BaseExpression> right) {
return std::shared_ptr<BinaryBooleanFunctionExpression>(new BinaryBooleanFunctionExpression(left, right, BinaryBooleanFunctionExpression::OR));
}
std::shared_ptr<BaseExpression> getBoolVariable(const std::string name) {
return state->getBooleanVariable(name);
}
std::shared_ptr<BaseExpression> getIntVariable(const std::string name) {
return state->getIntegerVariable(name);
}
protected:
std::shared_ptr<VariableState> state;
private:
static std::shared_ptr<T> instanceObject;
};
template <typename T>
std::shared_ptr<T> BaseGrammar<T>::instanceObject;
}
}
}
#endif /* BASEGRAMMAR_H */

54
src/parser/PrismParser/BooleanExpressionGrammar.cpp

@ -1,53 +1,35 @@
#include "BooleanExpressionGrammar.h"
#include "IntegerExpressionGrammar.h"
#include "ConstBooleanExpressionGrammar.h"
namespace storm {
namespace parser {
namespace prism {
BooleanExpressionGrammar::BooleanExpressionGrammar(std::shared_ptr<VariableState>& state)
: BooleanExpressionGrammar::base_type(booleanExpression), state(state) {
IntegerExpressionGrammar intExpr(this->state);
: BooleanExpressionGrammar::base_type(booleanExpression), BaseGrammar(state) {
// This rule defines all identifiers that have not been previously used.
identifierName %= qi::as_string[qi::raw[qi::lexeme[((qi::alpha | qi::char_('_')) >> *(qi::alnum | qi::char_('_')))]]][ qi::_pass = phoenix::bind(&storm::parser::prism::VariableState::isIdentifier, this->state.get(), qi::_1) ];
identifierName.name("identifier");
freeIdentifierName %= qi::as_string[qi::raw[qi::lexeme[((qi::alpha | qi::char_('_')) >> *(qi::alnum | qi::char_('_')))]]][ qi::_pass = phoenix::bind(&storm::parser::prism::VariableState::isFreeIdentifier, this->state.get(), qi::_1) ];
freeIdentifierName.name("unused identifier");
// This block defines all literal expressions.
booleanLiteralExpression = qi::bool_[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BooleanLiteral>(qi::_1))];
booleanLiteralExpression.name("boolean literal");
booleanExpression %= orExpression;
booleanExpression.name("boolean expression");
orExpression = andExpression[qi::_val = qi::_1] >> *(qi::lit("|") >> andExpression)[qi::_val = phoenix::bind(&BaseGrammar::createOr, this, qi::_val, qi::_1)];
orExpression.name("boolean expression");
// This block defines all expressions that are variables.
std::shared_ptr<BaseExpression> boolvarexpr = std::shared_ptr<BaseExpression>(new VariableExpression(BaseExpression::bool_, std::numeric_limits<uint_fast64_t>::max(), "bool", std::shared_ptr<BaseExpression>(nullptr), std::shared_ptr<BaseExpression>(nullptr)));
booleanVariableExpression = identifierName[qi::_val = boolvarexpr];
booleanVariableExpression.name("boolean variable");
andExpression = notExpression[qi::_val = qi::_1] >> *(qi::lit("&") >> notExpression)[qi::_val = phoenix::bind(&BaseGrammar::createAnd, this, qi::_val, qi::_1)];
andExpression.name("boolean expression");
// This block defines all atomic expressions that are constant, i.e. literals and constants.
booleanConstantExpression %= (this->state->booleanConstants_ | booleanLiteralExpression);
booleanConstantExpression.name("boolean constant or literal");
notExpression = atomicBooleanExpression[qi::_val = qi::_1] | (qi::lit("!") >> atomicBooleanExpression)[qi::_val = phoenix::bind(&BaseGrammar::createNot, this, qi::_1)];
notExpression.name("boolean expression");
// This block defines all expressions of type boolean.
relativeExpression = (intExpr >> relations_ >> intExpr)[qi::_val = phoenix::construct<std::shared_ptr<storm::ir::expressions::BaseExpression>>(phoenix::new_<storm::ir::expressions::BinaryRelationExpression>(qi::_1, qi::_3, qi::_2))];
relativeExpression.name("relative expression");
atomicBooleanExpression %= (relativeExpression | booleanVariableExpression | qi::lit("(") >> booleanExpression >> qi::lit(")") | booleanConstantExpression);
atomicBooleanExpression %= (relativeExpression | booleanVariableExpression | qi::lit("(") >> booleanExpression >> qi::lit(")") | ConstBooleanExpressionGrammar::instance(this->state));
atomicBooleanExpression.name("boolean expression");
notExpression = atomicBooleanExpression[qi::_val = qi::_1] | (qi::lit("!") >> atomicBooleanExpression)[qi::_val = phoenix::construct<std::shared_ptr<UnaryBooleanFunctionExpression>>(phoenix::new_<UnaryBooleanFunctionExpression>(qi::_1, UnaryBooleanFunctionExpression::NOT))];
notExpression.name("boolean expression");
andExpression = notExpression[qi::_val = qi::_1] >> *(qi::lit("&") >> notExpression)[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryBooleanFunctionExpression>(qi::_val, qi::_1, BinaryBooleanFunctionExpression::AND))];
andExpression.name("boolean expression");
orExpression = andExpression[qi::_val = qi::_1] >> *(qi::lit("|") >> andExpression)[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryBooleanFunctionExpression>(qi::_val, qi::_1, BinaryBooleanFunctionExpression::OR))];
orExpression.name("boolean expression");
booleanExpression %= orExpression;
booleanExpression.name("boolean expression");
// This block defines auxiliary entities that are used to check whether a certain variable exist.
booleanVariableName %= this->state->booleanVariableNames_;
booleanVariableName.name("boolean variable");
unassignedLocalBooleanVariableName %= this->state->localBooleanVariables_ - this->state->assignedLocalBooleanVariables_;
unassignedLocalBooleanVariableName.name("unassigned local boolean variable");
relativeExpression = (IntegerExpressionGrammar::instance(this->state) >> relations_ >> IntegerExpressionGrammar::instance(this->state))[qi::_val = phoenix::bind(&BaseGrammar::createRelation, this, qi::_1, qi::_2, qi::_3)];
relativeExpression.name("relative expression");
booleanVariableExpression = IdentifierGrammar::instance(this->state)[qi::_val = phoenix::bind(&BaseGrammar::getBoolVariable, this, qi::_1)];
booleanVariableExpression.name("boolean variable");
}
}

35
src/parser/PrismParser/BooleanExpressionGrammar.h

@ -10,52 +10,29 @@
#include "Includes.h"
#include "VariableState.h"
#include "IntegerExpressionGrammar.h"
#include "IdentifierGrammars.h"
#include "Tokens.h"
#include <iostream>
namespace storm {
namespace parser {
namespace prism {
class BooleanExpressionGrammar : public qi::grammar<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Skipper> {
class BooleanExpressionGrammar : public qi::grammar<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Unused>, public BaseGrammar<BooleanExpressionGrammar> {
public:
BooleanExpressionGrammar(std::shared_ptr<VariableState>& state);
private:
// Rules for variable/command names.
qi::rule<Iterator, std::string(), Skipper> integerVariableName;
qi::rule<Iterator, std::string(), Skipper> booleanVariableName;
qi::rule<Iterator, std::string(), Skipper> unassignedLocalBooleanVariableName;
qi::rule<Iterator, std::string(), Skipper> unassignedLocalIntegerVariableName;
qi::rule<Iterator, std::string(), Skipper> freeIdentifierName;
qi::rule<Iterator, std::string(), Skipper> identifierName;
// The starting point for arbitrary expressions.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> expression;
// Rules with boolean result type.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Skipper> booleanExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Unused> booleanExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> orExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> andExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> notExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> atomicBooleanExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> relativeExpression;
// Rules for variable recognition.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> booleanVariableExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> booleanVariableCreatorExpression;
// Rules for constant recognition.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> booleanConstantExpression;
// Rules for literal recognition.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> booleanLiteralExpression;
// A structure mapping the textual representation of a binary relation to the representation
// of the intermediate representation.
storm::parser::prism::relationalOperatorStruct relations_;
std::shared_ptr<storm::parser::prism::VariableState> state;
};

54
src/parser/PrismParser/ConstBooleanExpressionGrammar.cpp

@ -1,31 +1,53 @@
#include "ConstBooleanExpressionGrammar.h"
#include "ConstIntegerExpressionGrammar.h"
namespace storm {
namespace parser {
namespace prism {
std::shared_ptr<BaseExpression> ConstBooleanExpressionGrammar::createRelation(std::shared_ptr<BaseExpression> left, BinaryRelationExpression::RelationType relationType, std::shared_ptr<BaseExpression> right) {
return std::shared_ptr<BinaryRelationExpression>(new BinaryRelationExpression(left, right, relationType));
}
std::shared_ptr<BaseExpression> ConstBooleanExpressionGrammar::createNot(std::shared_ptr<BaseExpression> child) {
return std::shared_ptr<UnaryBooleanFunctionExpression>(new UnaryBooleanFunctionExpression(child, UnaryBooleanFunctionExpression::NOT));
}
std::shared_ptr<BaseExpression> ConstBooleanExpressionGrammar::createAnd(std::shared_ptr<BaseExpression> left, std::shared_ptr<BaseExpression> right) {
return std::shared_ptr<BinaryBooleanFunctionExpression>(new BinaryBooleanFunctionExpression(left, right, BinaryBooleanFunctionExpression::AND));
}
std::shared_ptr<BaseExpression> ConstBooleanExpressionGrammar::createOr(std::shared_ptr<BaseExpression> left, std::shared_ptr<BaseExpression> right) {
return std::shared_ptr<BinaryBooleanFunctionExpression>(new BinaryBooleanFunctionExpression(left, right, BinaryBooleanFunctionExpression::OR));
}
std::shared_ptr<BaseExpression> ConstBooleanExpressionGrammar::createLiteral(const bool value) {
return std::shared_ptr<BooleanLiteral>(new BooleanLiteral(value));
}
ConstBooleanExpressionGrammar::ConstBooleanExpressionGrammar(std::shared_ptr<VariableState>& state)
: ConstBooleanExpressionGrammar::base_type(constantBooleanExpression), state(state) {
: ConstBooleanExpressionGrammar::base_type(constantBooleanExpression), BaseGrammar(state) {
ConstIntegerExpressionGrammar constIntExpr(this->state);
constantBooleanExpression %= constantOrExpression;
constantBooleanExpression.name("constant boolean expression");
constantOrExpression = constantAndExpression[qi::_val = qi::_1] >> *(qi::lit("|") >> constantAndExpression)[qi::_val = phoenix::bind(&ConstBooleanExpressionGrammar::createOr, this, qi::_val, qi::_1)];
constantOrExpression.name("constant boolean expression");
constantAndExpression = constantNotExpression[qi::_val = qi::_1] >> *(qi::lit("&") >> constantNotExpression)[qi::_val = phoenix::bind(&ConstBooleanExpressionGrammar::createAnd, this, qi::_val, qi::_1)];
constantAndExpression.name("constant boolean expression");
constantNotExpression = constantAtomicBooleanExpression[qi::_val = qi::_1] | (qi::lit("!") >> constantAtomicBooleanExpression)[qi::_val = phoenix::bind(&ConstBooleanExpressionGrammar::createNot, this, qi::_1)];
constantNotExpression.name("constant boolean expression");
booleanLiteralExpression = qi::bool_[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BooleanLiteral>(qi::_1))];
booleanLiteralExpression.name("boolean literal");
booleanConstantExpression %= (this->state->booleanConstants_ | booleanLiteralExpression);
booleanConstantExpression.name("boolean constant or literal");
constantRelativeExpression = (constIntExpr >> relations_ >> constIntExpr)[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryRelationExpression>(qi::_1, qi::_3, qi::_2))];
constantRelativeExpression.name("constant boolean expression");
constantAtomicBooleanExpression %= (constantRelativeExpression | qi::lit("(") >> constantBooleanExpression >> qi::lit(")") | booleanLiteralExpression | booleanConstantExpression);
constantAtomicBooleanExpression.name("constant boolean expression");
constantNotExpression = constantAtomicBooleanExpression[qi::_val = qi::_1] | (qi::lit("!") >> constantAtomicBooleanExpression)[qi::_val = phoenix::construct<std::shared_ptr<UnaryBooleanFunctionExpression>>(phoenix::new_<UnaryBooleanFunctionExpression>(qi::_1, UnaryBooleanFunctionExpression::NOT))];
constantNotExpression.name("constant boolean expression");
constantAndExpression = constantNotExpression[qi::_val = qi::_1] >> *(qi::lit("&") >> constantNotExpression)[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryBooleanFunctionExpression>(qi::_val, qi::_1, BinaryBooleanFunctionExpression::AND))];
constantAndExpression.name("constant boolean expression");
constantOrExpression = constantAndExpression[qi::_val = qi::_1] >> *(qi::lit("|") >> constantAndExpression)[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryBooleanFunctionExpression>(qi::_val, qi::_1, BinaryBooleanFunctionExpression::OR))];
constantOrExpression.name("constant boolean expression");
constantBooleanExpression %= constantOrExpression;
constantBooleanExpression.name("constant boolean expression");
constantRelativeExpression = (ConstIntegerExpressionGrammar::instance(this->state) >> relations_ >> ConstIntegerExpressionGrammar::instance(this->state))[qi::_val = phoenix::bind(&ConstBooleanExpressionGrammar::createRelation, this, qi::_1, qi::_2, qi::_3)];
constantRelativeExpression.name("constant boolean expression");
booleanConstantExpression %= (this->state->booleanConstants_ | booleanLiteralExpression);
booleanConstantExpression.name("boolean constant or literal");
booleanLiteralExpression = qi::bool_[qi::_val = phoenix::bind(&ConstBooleanExpressionGrammar::createLiteral, this, qi::_1)];
booleanLiteralExpression.name("boolean literal");
}
}
}

23
src/parser/PrismParser/ConstBooleanExpressionGrammar.h

@ -9,35 +9,36 @@
#define CONSTBOOLEANEXPRESSIONGRAMMAR_H
#include "Includes.h"
#include "ConstIntegerExpressionGrammar.h"
#include "VariableState.h"
#include "UtilityGrammars.h"
#include "IdentifierGrammars.h"
#include "Tokens.h"
namespace storm {
namespace parser {
namespace prism {
class ConstBooleanExpressionGrammar : public qi::grammar<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Skipper> {
class ConstBooleanExpressionGrammar : public qi::grammar<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Unused>, public BaseGrammar<ConstBooleanExpressionGrammar> {
public:
ConstBooleanExpressionGrammar(std::shared_ptr<VariableState>& state);
private:
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> booleanLiteralExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> booleanConstantExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> relativeExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Skipper> constantBooleanExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Unused> constantBooleanExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantOrExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantAndExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantNotExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantAtomicBooleanExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantRelativeExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> booleanConstantExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> booleanLiteralExpression;
storm::parser::prism::relationalOperatorStruct relations_;
std::shared_ptr<storm::parser::prism::VariableState> state;
std::shared_ptr<BaseExpression> createRelation(std::shared_ptr<BaseExpression> left, BinaryRelationExpression::RelationType relationType, std::shared_ptr<BaseExpression> right);
std::shared_ptr<BaseExpression> createNot(std::shared_ptr<BaseExpression> child);
std::shared_ptr<BaseExpression> createAnd(std::shared_ptr<BaseExpression> left, std::shared_ptr<BaseExpression> right);
std::shared_ptr<BaseExpression> createOr(std::shared_ptr<BaseExpression> left, std::shared_ptr<BaseExpression> right);
std::shared_ptr<BaseExpression> createLiteral(const bool value);
};

53
src/parser/PrismParser/ConstDoubleExpressionGrammar.cpp

@ -0,0 +1,53 @@
#include "ConstDoubleExpressionGrammar.h"
namespace storm {
namespace parser {
namespace prism {
std::shared_ptr<BaseExpression> ConstDoubleExpressionGrammar::createLiteral(double value) {
return std::shared_ptr<DoubleLiteral>(new DoubleLiteral(value));
}
std::shared_ptr<BaseExpression> ConstDoubleExpressionGrammar::createPlus(const std::shared_ptr<BaseExpression> left, bool addition, const std::shared_ptr<BaseExpression> right) {
if (addition) {
return std::shared_ptr<BinaryNumericalFunctionExpression>(new BinaryNumericalFunctionExpression(BaseExpression::double_, left, right, BinaryNumericalFunctionExpression::PLUS));
} else {
return std::shared_ptr<BinaryNumericalFunctionExpression>(new BinaryNumericalFunctionExpression(BaseExpression::double_, left, right, BinaryNumericalFunctionExpression::MINUS));
}
}
std::shared_ptr<BaseExpression> ConstDoubleExpressionGrammar::createMult(const std::shared_ptr<BaseExpression> left, bool multiplication, const std::shared_ptr<BaseExpression> right) {
if (multiplication) {
return std::shared_ptr<BinaryNumericalFunctionExpression>(new BinaryNumericalFunctionExpression(BaseExpression::double_, left, right, BinaryNumericalFunctionExpression::TIMES));
} else {
return std::shared_ptr<BinaryNumericalFunctionExpression>(new BinaryNumericalFunctionExpression(BaseExpression::double_, left, right, BinaryNumericalFunctionExpression::DIVIDE));
}
}
ConstDoubleExpressionGrammar::ConstDoubleExpressionGrammar(std::shared_ptr<VariableState>& state)
: ConstDoubleExpressionGrammar::base_type(constantDoubleExpression), BaseGrammar(state) {
constantDoubleExpression %= constantDoublePlusExpression;
constantDoubleExpression.name("constant double expression");
constantDoublePlusExpression %= constantDoubleMultExpression[qi::_val = qi::_1] >> *((qi::lit("+")[qi::_a = true] | qi::lit("-")[qi::_a = false]) >> constantDoubleMultExpression)
[phoenix::bind(&ConstDoubleExpressionGrammar::createPlus, this, qi::_val, qi::_a, qi::_1)];
constantDoublePlusExpression.name("constant double expression");
constantDoubleMultExpression %= constantAtomicDoubleExpression[qi::_val = qi::_1] >> *((qi::lit("*")[qi::_a = true] | qi::lit("/")[qi::_a = false]) >> constantAtomicDoubleExpression)
[phoenix::bind(&ConstDoubleExpressionGrammar::createMult, this, qi::_val, qi::_a, qi::_1)];
constantDoubleMultExpression.name("constant double expression");
constantAtomicDoubleExpression %= (qi::lit("(") >> constantDoubleExpression >> qi::lit(")") | doubleConstantExpression);
constantAtomicDoubleExpression.name("constant double expression");
doubleConstantExpression %= (this->state->doubleConstants_ | doubleLiteralExpression);
doubleConstantExpression.name("double constant or literal");
doubleLiteralExpression = qi::double_[qi::_val = phoenix::bind(&ConstDoubleExpressionGrammar::createLiteral, this, qi::_1)];
doubleLiteralExpression.name("double literal");
}
}
}
}

43
src/parser/PrismParser/ConstDoubleExpressionGrammar.h

@ -0,0 +1,43 @@
/*
* File: ConstDoubleExpressionGrammar.h
* Author: nafur
*
* Created on April 10, 2013, 7:04 PM
*/
#ifndef CONSTDOUBLEEXPRESSIONGRAMMAR_H
#define CONSTDOUBLEEXPRESSIONGRAMMAR_H
#include "Includes.h"
#include "VariableState.h"
#include "IdentifierGrammars.h"
namespace storm {
namespace parser {
namespace prism {
class ConstDoubleExpressionGrammar : public qi::grammar<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Unused>, public BaseGrammar<ConstDoubleExpressionGrammar> {
public:
ConstDoubleExpressionGrammar(std::shared_ptr<VariableState>& state);
private:
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Unused> constantDoubleExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), qi::locals<bool>, Skipper> constantDoublePlusExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), qi::locals<bool>, Skipper> constantDoubleMultExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantAtomicDoubleExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> doubleConstantExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> doubleLiteralExpression;
std::shared_ptr<BaseExpression> createLiteral(double value);
std::shared_ptr<BaseExpression> createPlus(const std::shared_ptr<BaseExpression> left, bool addition, const std::shared_ptr<BaseExpression> right);
std::shared_ptr<BaseExpression> createMult(const std::shared_ptr<BaseExpression> left, bool multiplication, const std::shared_ptr<BaseExpression> right);
};
}
}
}
#endif /* CONSTDOUBLEEXPRESSIONGRAMMAR_H */

29
src/parser/PrismParser/ConstIntegerExpressionGrammar.cpp

@ -1,27 +1,32 @@
#include "ConstIntegerExpressionGrammar.h"
namespace storm {
namespace parser {
namespace prism {
ConstIntegerExpressionGrammar::ConstIntegerExpressionGrammar(std::shared_ptr<VariableState>& state)
: ConstIntegerExpressionGrammar::base_type(constantIntegerExpression), state(state) {
: ConstIntegerExpressionGrammar::base_type(constantIntegerExpression), BaseGrammar(state) {
integerLiteralExpression = qi::int_[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<IntegerLiteral>(qi::_1))];
integerLiteralExpression.name("integer literal");
integerConstantExpression %= (this->state->integerConstants_ | integerLiteralExpression);
integerConstantExpression.name("integer constant or literal");
constantIntegerExpression %= constantIntegerPlusExpression;
constantIntegerExpression.name("constant integer expression");
constantIntegerPlusExpression = constantIntegerMultExpression[qi::_val = qi::_1] >> *((qi::lit("+")[qi::_a = true] | qi::lit("-")[qi::_a = false]) >> constantIntegerMultExpression)
[qi::_val = phoenix::bind(&BaseGrammar::createIntPlus, this, qi::_val, qi::_a, qi::_1)];
constantIntegerPlusExpression.name("constant integer expression");
constantIntegerMultExpression %= constantAtomicIntegerExpression[qi::_val = qi::_1] >> *(qi::lit("*") >> constantAtomicIntegerExpression)
[qi::_val = phoenix::bind(&BaseGrammar::createIntMult, this, qi::_val, qi::_1)];
constantIntegerMultExpression.name("constant integer expression");
constantAtomicIntegerExpression %= (qi::lit("(") >> constantIntegerExpression >> qi::lit(")") | integerConstantExpression);
constantAtomicIntegerExpression.name("constant integer expression");
constantIntegerMultExpression %= constantAtomicIntegerExpression[qi::_val = qi::_1] >> *(qi::lit("*") >> constantAtomicIntegerExpression)[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryNumericalFunctionExpression>(BaseExpression::int_, qi::_val, qi::_1, BinaryNumericalFunctionExpression::TIMES))];
constantIntegerMultExpression.name("constant integer expression");
constantIntegerPlusExpression = constantIntegerMultExpression[qi::_val = qi::_1] >> *((qi::lit("+")[qi::_a = true] | qi::lit("-")[qi::_a = false]) >> constantIntegerMultExpression)[phoenix::if_(qi::_a) [qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryNumericalFunctionExpression>(BaseExpression::int_, qi::_val, qi::_1, BinaryNumericalFunctionExpression::PLUS)) ] .else_ [qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryNumericalFunctionExpression>(BaseExpression::int_, qi::_val, qi::_1, BinaryNumericalFunctionExpression::MINUS))]];
constantIntegerPlusExpression.name("constant integer expression");
constantIntegerExpression %= constantIntegerPlusExpression;
constantIntegerExpression.name("constant integer expression");
integerConstantExpression %= (this->state->integerConstants_ | integerLiteralExpression);
integerConstantExpression.name("integer constant or literal");
integerLiteralExpression = qi::int_[qi::_val = phoenix::bind(&BaseGrammar::createIntLiteral, this, qi::_1)];
integerLiteralExpression.name("integer literal");
}

11
src/parser/PrismParser/ConstIntegerExpressionGrammar.h

@ -10,24 +10,23 @@
#include "Includes.h"
#include "VariableState.h"
#include "IdentifierGrammars.h"
namespace storm {
namespace parser {
namespace prism {
class ConstIntegerExpressionGrammar : public qi::grammar<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Skipper> {
class ConstIntegerExpressionGrammar : public qi::grammar<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Unused>, public BaseGrammar<ConstIntegerExpressionGrammar> {
public:
ConstIntegerExpressionGrammar(std::shared_ptr<VariableState>& state);
private:
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> integerLiteralExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> integerConstantExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Skipper> constantIntegerExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Unused> constantIntegerExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), qi::locals<bool>, Skipper> constantIntegerPlusExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantIntegerMultExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantAtomicIntegerExpression;
std::shared_ptr<VariableState> state;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> integerConstantExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> integerLiteralExpression;
};

23
src/parser/PrismParser/IdentifierGrammars.cpp

@ -0,0 +1,23 @@
#include "IdentifierGrammars.h"
namespace storm {
namespace parser {
namespace prism {
IdentifierGrammar::IdentifierGrammar(std::shared_ptr<VariableState>& state)
: IdentifierGrammar::base_type(identifierName), BaseGrammar(state) {
identifierName %= qi::as_string[qi::raw[qi::lexeme[((qi::alpha | qi::char_('_')) >> *(qi::alnum | qi::char_('_')))]]][ qi::_pass = phoenix::bind(&VariableState::isIdentifier, this->state.get(), qi::_1) ];
identifierName.name("identifier");
}
FreeIdentifierGrammar::FreeIdentifierGrammar(std::shared_ptr<VariableState>& state)
: FreeIdentifierGrammar::base_type(freeIdentifierName), BaseGrammar(state) {
freeIdentifierName %= qi::as_string[qi::raw[qi::lexeme[((qi::alpha | qi::char_('_')) >> *(qi::alnum | qi::char_('_')))]]][ qi::_pass = phoenix::bind(&VariableState::isFreeIdentifier, this->state.get(), qi::_1) ];
freeIdentifierName.name("identifier");
}
}
}
}

36
src/parser/PrismParser/IdentifierGrammars.h

@ -0,0 +1,36 @@
/*
* File: Keywords.h
* Author: nafur
*
* Created on April 10, 2013, 6:03 PM
*/
#ifndef IDENTIFIERGRAMMARS_H
#define IDENTIFIERGRAMMARS_H
#include "Includes.h"
#include "BaseGrammar.h"
#include "VariableState.h"
namespace storm {
namespace parser {
namespace prism {
class IdentifierGrammar : public qi::grammar<Iterator, std::string(), Skipper, Unused>, public BaseGrammar<IdentifierGrammar> {
public:
IdentifierGrammar(std::shared_ptr<VariableState>& state);
private:
qi::rule<Iterator, std::string(), Skipper> identifierName;
};
class FreeIdentifierGrammar : public qi::grammar<Iterator, std::string(), Skipper, Unused>, public BaseGrammar<IdentifierGrammar> {
public:
FreeIdentifierGrammar(std::shared_ptr<VariableState>& state);
private:
qi::rule<Iterator, std::string(), Skipper> freeIdentifierName;
};
}
}
}
#endif /* IDENTIFIERGRAMMARS_H */

6
src/parser/PrismParser/Includes.h

@ -8,6 +8,8 @@
#ifndef BOOSTINCLUDES_H
#define BOOSTINCLUDES_H
#define DEBUGPRISM
// Used for Boost spirit.
#include <boost/typeof/typeof.hpp>
#include <boost/spirit/include/qi.hpp>
@ -24,12 +26,12 @@ typedef std::string::const_iterator BaseIteratorType;
typedef boost::spirit::classic::position_iterator2<BaseIteratorType> PositionIteratorType;
typedef PositionIteratorType Iterator;
typedef BOOST_TYPEOF(boost::spirit::ascii::space | qi::lit("//") >> *(qi::char_ - qi::eol) >> qi::eol) Skipper;
typedef BOOST_TYPEOF(qi::lit("//") >> *(qi::char_ - qi::eol) >> qi::eol | boost::spirit::ascii::space) Skipper2;
typedef boost::spirit::unused_type Unused;
#include "src/ir/IR.h"
using namespace storm::ir;
using namespace storm::ir::expressions;
#include "UtilityGrammars.h"
#endif /* BOOSTINCLUDES_H */

55
src/parser/PrismParser/IntegerExpressionGrammar.cpp

@ -1,45 +1,30 @@
#include "IntegerExpressionGrammar.h"
#include "IdentifierGrammars.h"
#include "ConstIntegerExpressionGrammar.h"
namespace storm {
namespace parser {
namespace prism {
IntegerExpressionGrammar::IntegerExpressionGrammar(std::shared_ptr<VariableState>& state)
: IntegerExpressionGrammar::base_type(integerExpression), state(state) {
// This rule defines all identifiers that have not been previously used.
identifierName %= qi::as_string[qi::raw[qi::lexeme[((qi::alpha | qi::char_('_')) >> *(qi::alnum | qi::char_('_')))]]][ qi::_pass = phoenix::bind(&VariableState::isIdentifier, this->state.get(), qi::_1) ];
identifierName.name("identifier");
// This block defines all literal expressions.
integerLiteralExpression = qi::int_[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<IntegerLiteral>(qi::_1))];
integerLiteralExpression.name("integer literal");
// This block defines all expressions that are variables.
std::shared_ptr<BaseExpression> intvarexpr = std::shared_ptr<BaseExpression>(new VariableExpression(BaseExpression::int_, std::numeric_limits<uint_fast64_t>::max(), "int", std::shared_ptr<BaseExpression>(nullptr), std::shared_ptr<BaseExpression>(nullptr)));
integerVariableExpression = identifierName[qi::_val = intvarexpr];
integerVariableExpression.name("integer variable");
// This block defines all atomic expressions that are constant, i.e. literals and constants.
integerConstantExpression %= (this->state->integerConstants_ | integerLiteralExpression);
integerConstantExpression.name("integer constant or literal");
// This block defines all expressions of integral type.
atomicIntegerExpression %= (integerVariableExpression | qi::lit("(") >> integerExpression >> qi::lit(")") | integerConstantExpression);
atomicIntegerExpression.name("integer expression");
integerMultExpression %= atomicIntegerExpression[qi::_val = qi::_1] >> *(qi::lit("*") >> atomicIntegerExpression)[qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryNumericalFunctionExpression>(BaseExpression::int_, qi::_val, qi::_1, BinaryNumericalFunctionExpression::TIMES))];
integerMultExpression.name("integer expression");
integerPlusExpression = integerMultExpression[qi::_val = qi::_1] >> *((qi::lit("+")[qi::_a = true] | qi::lit("-")[qi::_a = false]) >> integerMultExpression)[phoenix::if_(qi::_a) [qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryNumericalFunctionExpression>(BaseExpression::int_, qi::_val, qi::_1, BinaryNumericalFunctionExpression::PLUS)) ] .else_ [qi::_val = phoenix::construct<std::shared_ptr<BaseExpression>>(phoenix::new_<BinaryNumericalFunctionExpression>(BaseExpression::int_, qi::_val, qi::_1, BinaryNumericalFunctionExpression::MINUS))]];
integerPlusExpression.name("integer expression");
integerExpression %= integerPlusExpression;
integerExpression.name("integer expression");
}
IntegerExpressionGrammar::IntegerExpressionGrammar(std::shared_ptr<VariableState>& state)
: IntegerExpressionGrammar::base_type(integerExpression), BaseGrammar(state) {
void IntegerExpressionGrammar::prepareForSecondRun() {
// Override variable expressions: only allow declared variables.
integerVariableExpression %= this->state->integerVariables_;
integerVariableExpression.name("integer variable");
}
integerExpression %= integerPlusExpression;
integerExpression.name("integer expression");
integerPlusExpression = integerMultExpression[qi::_val = qi::_1] >> *((qi::lit("+")[qi::_a = true] | qi::lit("-")[qi::_a = false]) >> integerMultExpression)[qi::_val = phoenix::bind(&BaseGrammar::createIntPlus, this, qi::_val, qi::_a, qi::_1)];
integerPlusExpression.name("integer expression");
integerMultExpression %= atomicIntegerExpression[qi::_val = qi::_1] >> *(qi::lit("*") >> atomicIntegerExpression[qi::_val = phoenix::bind(&BaseGrammar::createIntMult, this, qi::_val, qi::_1)]);
integerMultExpression.name("integer expression");
atomicIntegerExpression %= (integerVariableExpression | qi::lit("(") >> integerExpression >> qi::lit(")") | ConstIntegerExpressionGrammar::instance(this->state));
atomicIntegerExpression.name("integer expression");
integerVariableExpression = IdentifierGrammar::instance(this->state)[qi::_val = phoenix::bind(&BaseGrammar::getIntVariable, this, qi::_1)];
integerVariableExpression.name("integer variable");
}
}
}

28
src/parser/PrismParser/IntegerExpressionGrammar.h

@ -11,6 +11,7 @@
#include "src/ir/IR.h"
#include "VariableState.h"
#include "Includes.h"
#include "IdentifierGrammars.h"
#include <memory>
@ -18,39 +19,16 @@ namespace storm {
namespace parser {
namespace prism {
class IntegerExpressionGrammar : public qi::grammar<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Skipper> {
class IntegerExpressionGrammar : public qi::grammar<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Unused>, public BaseGrammar<IntegerExpressionGrammar> {
public:
IntegerExpressionGrammar(std::shared_ptr<VariableState>& state);
void prepareForSecondRun();
private:
qi::rule<Iterator, std::string(), Skipper> identifierName;
// The starting point for arbitrary expressions.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> expression;
// Rules with integer result type.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Skipper> integerExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper, Unused> integerExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), qi::locals<bool>, Skipper> integerPlusExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> integerMultExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> atomicIntegerExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantIntegerExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), qi::locals<bool>, Skipper> constantIntegerPlusExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantIntegerMultExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> constantAtomicIntegerExpression;
// Rules for variable recognition.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> integerVariableExpression;
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), qi::locals<std::shared_ptr<BaseExpression>>, Skipper> integerVariableCreatorExpression;
// Rules for constant recognition.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> integerConstantExpression;
// Rules for literal recognition.
qi::rule<Iterator, std::shared_ptr<BaseExpression>(), Skipper> integerLiteralExpression;
std::shared_ptr<VariableState> state;
};
}

46
src/parser/PrismParser/UtilityGrammars.h → src/parser/PrismParser/Tokens.h

@ -1,20 +1,33 @@
/*
* File: Keywords.h
* File: Tokens.h
* Author: nafur
*
* Created on April 10, 2013, 6:03 PM
* Created on April 19, 2013, 11:17 PM
*/
#ifndef KEYWORDS_H
#define KEYWORDS_H
#include "Includes.h"
#ifndef TOKENS_H
#define TOKENS_H
namespace storm {
namespace parser {
namespace prism {
// A structure defining the keywords that are not allowed to be chosen as identifiers.
// A structure mapping the textual representation of a model type to the model type
// representation of the intermediate representation.
struct modelTypeStruct : qi::symbols<char, Program::ModelType> {
modelTypeStruct() {
add
("dtmc", Program::ModelType::DTMC)
("ctmc", Program::ModelType::CTMC)
("mdp", Program::ModelType::MDP)
("ctmdp", Program::ModelType::CTMDP)
;
}
};
// A structure defining the keywords that are not allowed to be chosen as identifiers.
struct keywordsStruct : qi::symbols<char, unsigned> {
keywordsStruct() {
add
@ -34,20 +47,7 @@ namespace prism {
;
}
};
// A structure mapping the textual representation of a model type to the model type
// representation of the intermediate representation.
struct modelTypeStruct : qi::symbols<char, Program::ModelType> {
modelTypeStruct() {
add
("dtmc", Program::ModelType::DTMC)
("ctmc", Program::ModelType::CTMC)
("mdp", Program::ModelType::MDP)
("ctmdp", Program::ModelType::CTMDP)
;
}
};
// A structure mapping the textual representation of a binary relation to the representation
// of the intermediate representation.
struct relationalOperatorStruct : qi::symbols<char, BinaryRelationExpression::RelationType> {
@ -61,9 +61,9 @@ namespace prism {
;
}
};
}
}
}
#endif /* KEYWORDS_H */
#endif /* TOKENS_H */

90
src/parser/PrismParser/VariableState.h

@ -10,6 +10,7 @@
#include "src/ir/IR.h"
#include "Includes.h"
#include "Tokens.h"
namespace storm {
namespace parser {
@ -18,14 +19,15 @@ namespace prism {
using namespace storm::ir;
using namespace storm::ir::expressions;
struct VariableState : public storm::ir::VariableAdder {
public:
VariableState()
: keywords(), nextBooleanVariableIndex(0), nextIntegerVariableIndex(0)
{
public:
VariableState(bool firstRun = true)
: firstRun(firstRun), keywords(), nextBooleanVariableIndex(0), nextIntegerVariableIndex(0) {
}
bool firstRun;
keywordsStruct keywords;
// Used for indexing the variables.
@ -43,30 +45,81 @@ struct VariableState : public storm::ir::VariableAdder {
localBooleanVariables_, localIntegerVariables_, assignedLocalBooleanVariables_, assignedLocalIntegerVariables_;
uint_fast64_t addBooleanVariable(const std::string& name, const std::shared_ptr<storm::ir::expressions::BaseExpression> init) {
std::cerr << "adding boolean variable " << name << std::endl;
if (firstRun) {
std::shared_ptr<VariableExpression> varExpr = std::shared_ptr<VariableExpression>(new VariableExpression(storm::ir::expressions::BaseExpression::bool_, this->nextBooleanVariableIndex, name));
this->booleanVariables_.add(name, varExpr);
this->booleanVariableNames_.add(name, name);
this->nextBooleanVariableIndex++;
return this->nextBooleanVariableIndex-1;
} else {
std::shared_ptr<VariableExpression> res = this->booleanVariables_.at(name);
if (res != nullptr) {
return res->getVariableIndex();
} else {
std::cerr << "Variable " << name << " was not created in first run" << std::endl;
return 0;
}
}
}
uint_fast64_t addIntegerVariable(const std::string& name, const std::shared_ptr<storm::ir::expressions::BaseExpression> lower, const std::shared_ptr<storm::ir::expressions::BaseExpression> upper, const std::shared_ptr<storm::ir::expressions::BaseExpression> init) {
std::cerr << "adding integer variable " << name << std::endl;
if (firstRun) {
std::shared_ptr<VariableExpression> varExpr = std::shared_ptr<VariableExpression>(new VariableExpression(storm::ir::expressions::BaseExpression::int_, this->nextIntegerVariableIndex, name, lower, upper));
this->integerVariables_.add(name, varExpr);
this->integerVariableNames_.add(name, name);
this->nextIntegerVariableIndex++;
return this->nextIntegerVariableIndex-1;
} else {
std::shared_ptr<VariableExpression> res = this->integerVariables_.at(name);
if (res != nullptr) {
return res->getVariableIndex();
} else {
std::cerr << "Variable " << name << " was not created in first run" << std::endl;
return 0;
}
}
}
std::shared_ptr<VariableExpression> getBooleanVariable(const std::string& name) {
std::cerr << "getting boolen variable " << name << std::endl;
std::shared_ptr<VariableExpression> res = this->booleanVariables_.at(name);
if (res != nullptr) {
return res->getVariableIndex();
return res;
} else {
if (firstRun) {
return std::shared_ptr<VariableExpression>(new VariableExpression(BaseExpression::bool_, std::numeric_limits<uint_fast64_t>::max(), "bool", std::shared_ptr<BaseExpression>(nullptr), std::shared_ptr<BaseExpression>(nullptr)));
} else {
std::cerr << "Variable " << name << " was not created in first run" << std::endl;
return std::shared_ptr<VariableExpression>(nullptr);
}
}
std::shared_ptr<VariableExpression> varExpr = std::shared_ptr<VariableExpression>(new VariableExpression(storm::ir::expressions::BaseExpression::bool_, this->nextBooleanVariableIndex, name));
this->booleanVariables_.add(name, varExpr);
this->booleanVariableNames_.add(name, name);
this->nextBooleanVariableIndex++;
return this->nextBooleanVariableIndex-1;
}
uint_fast64_t addIntegerVariable(const std::string& name, const std::shared_ptr<storm::ir::expressions::BaseExpression> lower, const std::shared_ptr<storm::ir::expressions::BaseExpression> upper, const std::shared_ptr<storm::ir::expressions::BaseExpression> init) {
std::shared_ptr<VariableExpression> getIntegerVariable(const std::string& name) {
std::cerr << "getting integer variable " << name << std::endl;
std::shared_ptr<VariableExpression> res = this->integerVariables_.at(name);
if (res != nullptr) {
return res->getVariableIndex();
return res;
} else {
if (firstRun) {
return std::shared_ptr<VariableExpression>(new VariableExpression(BaseExpression::int_, std::numeric_limits<uint_fast64_t>::max(), "int", std::shared_ptr<BaseExpression>(nullptr), std::shared_ptr<BaseExpression>(nullptr)));
} else {
std::cerr << "Variable " << name << " was not created in first run" << std::endl;
return std::shared_ptr<VariableExpression>(nullptr);
}
}
std::shared_ptr<VariableExpression> varExpr = std::shared_ptr<VariableExpression>(new VariableExpression(storm::ir::expressions::BaseExpression::int_, this->nextIntegerVariableIndex, name, lower, upper));
this->integerVariables_.add(name, varExpr);
this->integerVariableNames_.add(name, name);
this->nextIntegerVariableIndex++;
return this->nextIntegerVariableIndex-1;
}
void startModule() {
std::cerr << "starting new module" << std::endl;
this->localBooleanVariables_.clear();
this->localIntegerVariables_.clear();
}
bool isFreeIdentifier(std::string& s) const {
std::cerr << "Checking if " << s << " is free" << std::endl;
if (this->integerVariableNames_.find(s) != nullptr) return false;
if (this->allConstantNames_.find(s) != nullptr) return false;
if (this->labelNames_.find(s) != nullptr) return false;
@ -75,16 +128,19 @@ struct VariableState : public storm::ir::VariableAdder {
return true;
}
bool isIdentifier(std::string& s) const {
std::cerr << "Checking if " << s << " is identifier" << std::endl;
if (this->allConstantNames_.find(s) != nullptr) return false;
if (this->keywords.find(s) != nullptr) return false;
return true;
}
void prepareForSecondRun() {
std::cerr << "starting second run" << std::endl;
integerConstants_.clear();
booleanConstants_.clear();
doubleConstants_.clear();
allConstantNames_.clear();
this->firstRun = false;
}
};

Loading…
Cancel
Save