LCOV - code coverage report
Current view: top level - pbes/include/mcrl2/pbes - print.h (source / functions) Hit Total Coverage
Test: mcrl2_coverage.info.cleaned Lines: 134 136 98.5 %
Date: 2024-04-21 03:44:01 Functions: 55 91 60.4 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : // Author(s): Wieger Wesselink
       2             : // Copyright: see the accompanying file COPYING or copy at
       3             : // https://github.com/mCRL2org/mCRL2/blob/master/COPYING
       4             : //
       5             : // Distributed under the Boost Software License, Version 1.0.
       6             : // (See accompanying file LICENSE_1_0.txt or copy at
       7             : // http://www.boost.org/LICENSE_1_0.txt)
       8             : //
       9             : /// \file mcrl2/pbes/print.h
      10             : /// \brief add your file description here.
      11             : 
      12             : #ifndef MCRL2_PBES_PRINT_H
      13             : #define MCRL2_PBES_PRINT_H
      14             : 
      15             : #include "mcrl2/data/print.h"
      16             : #include "mcrl2/pbes/traverser.h"
      17             : 
      18             : namespace mcrl2 {
      19             : 
      20             : namespace pbes_system {
      21             : 
      22         335 : constexpr inline int precedence(const forall&) { return 21; }
      23         164 : constexpr inline int precedence(const exists&) { return 21; }
      24          23 : constexpr inline int precedence(const imp&)    { return 22; }
      25        8976 : constexpr inline int precedence(const or_&)    { return 23; }
      26        5659 : constexpr inline int precedence(const and_&)   { return 24; }
      27          38 : constexpr inline int precedence(const not_&)   { return 25; }
      28       16206 : inline int precedence(const pbes_expression& x)
      29             : {
      30       16206 :   if      (is_forall(x)) { return precedence(atermpp::down_cast<forall>(x)); }
      31       15871 :   else if (is_exists(x)) { return precedence(atermpp::down_cast<exists>(x)); }
      32       15707 :   else if (is_imp(x))    { return precedence(atermpp::down_cast<imp>(x)); }
      33       15702 :   else if (is_or(x))     { return precedence(atermpp::down_cast<or_>(x)); }
      34       11254 :   else if (is_and(x))    { return precedence(atermpp::down_cast<and_>(x)); }
      35        8819 :   else if (is_not(x))    { return precedence(atermpp::down_cast<not_>(x)); }
      36        8781 :   return core::detail::max_precedence;
      37             : }
      38             : 
      39             : // only defined for binary operators
      40           0 : inline bool is_left_associative(const imp&)  { return false; }
      41          81 : inline bool is_left_associative(const or_&)  { return true; }
      42         954 : inline bool is_left_associative(const and_&) { return true; }
      43             : inline bool is_left_associative(const pbes_expression& x)
      44             : {
      45             :   if (is_imp(x))      { return is_left_associative(atermpp::down_cast<imp>(x)); }
      46             :   else if (is_or(x))  { return is_left_associative(atermpp::down_cast<or_>(x)); }
      47             :   else if (is_and(x)) { return is_left_associative(atermpp::down_cast<and_>(x)); }
      48             :   return false;
      49             : }
      50             : 
      51           0 : inline bool is_right_associative(const imp&)  { return true; }
      52         841 : inline bool is_right_associative(const or_&)  { return true; }
      53        1258 : inline bool is_right_associative(const and_&) { return true; }
      54             : inline bool is_right_associative(const pbes_expression& x)
      55             : {
      56             :   if (is_imp(x))      { return is_right_associative(atermpp::down_cast<imp>(x)); }
      57             :   else if (is_or(x))  { return is_right_associative(atermpp::down_cast<or_>(x)); }
      58             :   else if (is_and(x)) { return is_right_associative(atermpp::down_cast<and_>(x)); }
      59             :   return false;
      60             : }
      61             : 
      62             : namespace detail {
      63             : 
      64             : template <typename Derived>
      65             : struct printer: public pbes_system::add_traverser_sort_expressions<data::detail::printer, Derived>
      66             : {
      67             :   typedef pbes_system::add_traverser_sort_expressions<data::detail::printer, Derived> super;
      68             : 
      69             :   using super::enter;
      70             :   using super::leave;
      71             :   using super::apply;
      72             :   using super::derived;
      73             :   using super::print_abstraction;
      74             :   using super::print_list;
      75             :   using super::print_variables;
      76             : 
      77             :   // N.B. We need a special version due to the "val" operator that needs to be
      78             :   // put around data expressions.
      79             :   template <typename T>
      80       16079 :   void print_pbes_expression(const T& x, bool needs_parentheses = false)
      81             :   {
      82       16079 :     bool is_data_expr = is_data(x);
      83       16079 :     if (is_data_expr)
      84             :     {
      85        4807 :       derived().print("val");
      86             :     }
      87       16079 :     if (needs_parentheses || is_data_expr)
      88             :     {
      89        8387 :       derived().print("(");
      90             :     }
      91       16079 :     derived().apply(x);
      92       16079 :     if (needs_parentheses || is_data_expr)
      93             :     {
      94        8387 :       derived().print(")");
      95             :     }
      96       16079 :   }
      97             : 
      98         333 :   void print_pbes_unary_operand(const pbes_expression& x, const pbes_expression& operand)
      99             :   {
     100         333 :     print_pbes_expression(operand, precedence(operand) < precedence(x));
     101         333 :   }
     102             : 
     103             :   // N.B. We need a special version due to the "val" operator that needs to be
     104             :   // put around data expressions.
     105             :   template <typename T>
     106          22 :   void print_pbes_unary_left_operation(const T& x, const std::string& op)
     107             :   {
     108          22 :     derived().print(op);
     109          22 :     print_pbes_unary_operand(x, x.operand());
     110          22 :   }
     111             : 
     112             :   // N.B. We need a special version due to the "val" operator that needs to be
     113             :   // put around data expressions.
     114             :   template <typename T>
     115        7770 :   void print_pbes_binary_operation(const T& x, const std::string& op)
     116             :   {
     117        7770 :     const auto& x1 = x.left();
     118        7770 :     const auto& x2 = x.right();
     119        7770 :     auto p = precedence(x);
     120        7770 :     auto p1 = precedence(x1);
     121        7770 :     auto p2 = precedence(x2);
     122        7770 :     print_pbes_expression(x1, (p1 < p) || (p1 == p && !is_left_associative(x)));
     123        7770 :     derived().print(op);
     124        7770 :     print_pbes_expression(x2, (p2 < p) || (p2 == p && !is_right_associative(x)));
     125        7770 :   }
     126             : 
     127             :   // N.B. We need a special version due to the "val" operator that needs to be
     128             :   // put around data expressions.
     129             :   template <typename Abstraction>
     130         311 :   void print_pbes_abstraction(const Abstraction& x, const std::string& op)
     131             :   {
     132         311 :     derived().enter(x);
     133         311 :     derived().print(op + " ");
     134         311 :     print_variables(x.variables(), true, true, false, "", "", ", ");
     135         311 :     derived().print(". ");
     136         311 :     print_pbes_unary_operand(x, x.body());
     137         311 :     derived().leave(x);
     138         311 :   }
     139             : 
     140         472 :   void apply(const pbes_system::propositional_variable& x)
     141             :   {
     142         472 :     derived().enter(x);
     143         472 :     derived().apply(x.name());
     144         472 :     print_variables(x.parameters());
     145         472 :     derived().leave(x);
     146         472 :   }
     147             : 
     148         483 :   void apply(const pbes_system::fixpoint_symbol& x)
     149             :   {
     150         483 :     derived().enter(x);
     151         483 :     derived().print(x.is_mu() ? "mu" : "nu");
     152         483 :     derived().leave(x);
     153         483 :   }
     154             : 
     155         395 :   void apply(const pbes_system::pbes_equation& x)
     156             :   {
     157         395 :     derived().enter(x);
     158         395 :     derived().apply(x.symbol());
     159         395 :     derived().print(" ");
     160         395 :     derived().apply(x.variable());
     161             :     // TODO: change the weird convention of putting the rhs of an equation on a new line
     162         395 :     derived().print(" =\n       ");
     163         395 :     bool print_val = data::is_data_expression(x.formula());
     164         395 :     if (print_val)
     165             :     {
     166          75 :       derived().print("val(");
     167             :     }
     168         395 :     derived().apply(x.formula());
     169         395 :     if (print_val)
     170             :     {
     171          75 :       derived().print(")");
     172             :     }
     173         395 :     derived().print(";");
     174         395 :     derived().leave(x);
     175         395 :   }
     176             : 
     177         206 :   void apply(const pbes_system::pbes& x)
     178             :   {
     179         206 :     derived().enter(x);
     180         206 :     derived().apply(x.data());
     181         206 :     print_variables(x.global_variables(), true, true, true, "glob ", ";\n\n", ";\n     ");
     182         206 :     print_list(x.equations(), "pbes ", "\n\n", "\n     ");
     183         206 :     derived().print("init ");
     184         206 :     print_pbes_expression(x.initial_state());
     185         206 :     derived().print(";\n");
     186         206 :     derived().leave(x);
     187         206 :   }
     188             : 
     189        9896 :   void apply(const pbes_system::propositional_variable_instantiation& x)
     190             :   {
     191        9896 :     derived().enter(x);
     192        9896 :     derived().apply(x.name());
     193        9896 :     print_list(x.parameters(), "(", ")", ", ", false);
     194        9896 :     derived().leave(x);
     195        9896 :   }
     196             : 
     197          22 :   void apply(const pbes_system::not_& x)
     198             :   {
     199          22 :     derived().enter(x);
     200          22 :     print_pbes_unary_left_operation(x, "!");
     201          22 :     derived().leave(x);
     202          22 :   }
     203             : 
     204        3224 :   void apply(const pbes_system::and_& x)
     205             :   {
     206        3224 :     derived().enter(x);
     207        3224 :     print_pbes_binary_operation(x, " && ");
     208        3224 :     derived().leave(x);
     209        3224 :   }
     210             : 
     211        4528 :   void apply(const pbes_system::or_& x)
     212             :   {
     213        4528 :     derived().enter(x);
     214        4528 :     print_pbes_binary_operation(x, " || ");
     215        4528 :     derived().leave(x);
     216        4528 :   }
     217             : 
     218          18 :   void apply(const pbes_system::imp& x)
     219             :   {
     220          18 :     derived().enter(x);
     221          18 :     print_pbes_binary_operation(x, " => ");
     222          18 :     derived().leave(x);
     223          18 :   }
     224             : 
     225         214 :   void apply(const pbes_system::forall& x)
     226             :   {
     227         214 :     derived().enter(x);
     228         214 :     print_pbes_abstraction(x, "forall");
     229         214 :     derived().leave(x);
     230         214 :   }
     231             : 
     232          97 :   void apply(const pbes_system::exists& x)
     233             :   {
     234          97 :     derived().enter(x);
     235          97 :     print_pbes_abstraction(x, "exists");
     236          97 :     derived().leave(x);
     237          97 :   }
     238             : };
     239             : 
     240             : } // namespace detail
     241             : 
     242             : /// \brief Prints the object x to a stream.
     243             : struct stream_printer
     244             : {
     245             :   template <typename T>
     246        6990 :   void operator()(const T& x, std::ostream& out)
     247             :   {
     248        6990 :     core::detail::apply_printer<pbes_system::detail::printer> printer(out);
     249        6990 :     printer.apply(x);
     250        6990 :   }
     251             : };
     252             : 
     253             : /// \brief Returns a string representation of the object x.
     254             : template <typename T>
     255        6990 : std::string pp(const T& x)
     256             : {
     257        6990 :   std::ostringstream out;
     258        6990 :   stream_printer()(x, out);
     259       13980 :   return out.str();
     260        6990 : }
     261             : 
     262             : } // namespace pbes_system
     263             : 
     264             : } // namespace mcrl2
     265             : 
     266             : #endif // MCRL2_PBES_PRINT_H

Generated by: LCOV version 1.14