11#ifndef MCRL2_DATA_DETAIL_REWR_JITTYC_H
12#define MCRL2_DATA_DETAIL_REWR_JITTYC_H
17#include "mcrl2/utilities/uncompiledlibrary.h"
18#include "mcrl2/utilities/toolset_version.h"
19#include "mcrl2/atermpp/standard_containers/vector.h"
20#include "mcrl2/data/detail/rewrite/jitty.h"
21#include "mcrl2/data/detail/rewrite/match_tree.h"
22#include "mcrl2/data/detail/rewrite/nfs_array.h"
23#include "mcrl2/data/substitutions/mutable_map_substitution.h"
25#ifdef MCRL2_ENABLE_JITTYC
34typedef std::vector < sort_expression_list> sort_list_vector;
42class normal_form_cache
45 std::set<data_expression> m_lookup;
53 normal_form_cache(
const normal_form_cache& ) =
delete;
54 normal_form_cache(normal_form_cache&& ) =
delete;
55 normal_form_cache& operator=(
const normal_form_cache& ) =
delete;
56 normal_form_cache& operator=(normal_form_cache&& ) =
delete;
65 std::string insert(
const data_expression& t)
68 const data_expression* cached_term = &*(m_lookup.insert(t).first);
69 ss <<
"*reinterpret_cast<const data_expression*>(" << (
void*)(cached_term) <<
")";
77 return m_lookup.empty();
85class RewriterCompilingJitty:
public Rewriter
88 typedef Rewriter::substitution_type substitution_type;
89 typedef void (*rewriter_function)(data_expression&,
const application&, RewriterCompilingJitty*);
91 RewriterCompilingJitty(
const data_specification& DataSpec,
const used_data_equation_selector&);
92 virtual ~RewriterCompilingJitty();
94 rewrite_strategy getStrategy();
96 data_expression rewrite(
const data_expression& term, substitution_type& sigma);
98 void rewrite(data_expression& result,
const data_expression& term, substitution_type& sigma);
102 substitution_type *global_sigma;
103 bool rewriting_in_progress;
104 rewrite_stack m_rewrite_stack;
108 std::vector<variable_list> rewriter_binding_variable_lists;
109 std::map <variable_list, std::size_t> variable_list_indices1;
117 std::size_t binding_variable_list_index(
const variable_list& vl)
119 if (variable_list_indices1.count(vl)>0)
121 return variable_list_indices1[vl];
123 const std::size_t index_for_vl=rewriter_binding_variable_lists.size();
124 variable_list_indices1[vl]=index_for_vl;
125 rewriter_binding_variable_lists.push_back(vl);
129 inline variable_list binding_variable_list_get(
const std::size_t i)
131 return (rewriter_binding_variable_lists[i]);
144 struct variable_index_where_stack_pair
146 std::size_t variable_index;
149 std::vector<std::string> declaration_stack;
152 variable_index_where_stack_pair(
const std::size_t& vi,
const std::vector<std::string>& ds)
153 : variable_index(vi),
154 declaration_stack(ds)
158 variable_index_where_stack_pair()
162 std::vector<variable> rewriter_bound_variables;
163 std::map <variable, variable_index_where_stack_pair > variable_indices0;
165 std::size_t bound_variable_index(
const variable& v)
167 assert(variable_indices0.count(v)>0);
168 assert(variable_indices0[v].declaration_stack.back().empty());
169 return variable_indices0[v].variable_index;
175 void bound_variable_index_declare(
const variable& v,
const std::string& name)
177 if (variable_indices0.count(v)>0)
179 variable_indices0[v].declaration_stack.push_back(name);
182 const std::size_t index_for_v=rewriter_bound_variables.size();
183 variable_indices0[v]=variable_index_where_stack_pair(index_for_v,std::vector<std::string>(1,name));
184 rewriter_bound_variables.push_back(v);
188 void bound_variables_index_declare(
const variable_list& vl)
190 for(
const variable& v: vl)
192 bound_variable_index_declare(v,
"");
196 void bound_variable_index_undeclare(
const variable& v)
198 assert(variable_indices0.count(v)>0);
199 assert(variable_indices0[v].declaration_stack.size()>0);
200 variable_indices0[v].declaration_stack.pop_back();
203 void bound_variables_index_undeclare(
const variable_list& vl)
205 for(
const variable& v: vl)
207 bound_variable_index_undeclare(v);
211 const variable& bound_variable_get(
const std::size_t i)
213 assert(i<rewriter_bound_variables.size());
214 return (rewriter_bound_variables[i]);
218 std::string bound_variable_stems_from_whr_clause(
const variable& v)
220 assert(variable_indices0.count(v)>0);
221 assert(variable_indices0[v].declaration_stack.size()>0);
222 return variable_indices0[v].declaration_stack.back();
229 std::size_t arity_bound;
230 std::size_t index_bound;
234 std::vector<rewriter_function> functions_when_arguments_are_not_in_normal_form;
235 std::vector<rewriter_function> functions_when_arguments_are_in_normal_form;
238 std::vector<data_expression> normal_forms_for_constants;
241 RewriterCompilingJitty& operator=(
const RewriterCompilingJitty& other)=
delete;
243 std::shared_ptr<detail::Rewriter> clone()
245 return std::shared_ptr<Rewriter>(
new RewriterCompilingJitty(*
this));
250 friend class ImplementTree;
252 RewriterJitty jitty_rewriter;
253 std::set < data_equation > rewrite_rules;
254 const match_tree dummy=match_tree();
256 std::map<function_symbol, data_equation_list> jittyc_eqns;
257 std::set<function_symbol> m_extra_symbols;
259 std::shared_ptr<uncompiled_library> rewriter_so;
260 std::shared_ptr<normal_form_cache> m_nf_cache;
268 atermpp::detail::thread_aterm_pool* m_thread_aterm_pool;
272 RewriterCompilingJitty(RewriterCompilingJitty& other) =
default;
274 void (*so_rewr_cleanup)();
275 void (*so_rewr)(data_expression& result,
const data_expression&, RewriterCompilingJitty*);
277 void add_base_nfs(nfs_array& a,
const function_symbol& opid, std::size_t arity);
278 void extend_nfs(nfs_array& a,
const function_symbol& opid, std::size_t arity);
279 bool opid_is_nf(
const function_symbol& opid, std::size_t num_args);
280 void calc_nfs_list(nfs_array& a,
const application& args, variable_or_number_list nnfvars);
281 bool calc_nfs(
const data_expression& t, variable_or_number_list nnfvars);
282 void CleanupRewriteSystem();
283 void BuildRewriteSystem();
284 void generate_code(
const std::string& filename);
285 void generate_rewr_functions(std::ostream& s,
const data::function_symbol& func,
const data_equation_list& eqs);
286 bool lift_rewrite_rule_to_right_arity(data_equation& e,
const std::size_t requested_arity);
287 sort_list_vector get_residual_sorts(
const sort_expression& s,
const std::size_t actual_arity,
const std::size_t requested_arity);
288 match_tree_list create_strategy(
const data_equation_list& rules,
const std::size_t arity);
289 void term2seq(
const data_expression& t, match_tree_list& s, std::size_t *var_cnt,
const bool omit_head);
290 match_tree_list create_sequence(
const data_equation& rule, std::size_t* var_cnt);
291 match_tree_list subst_var(
const match_tree_list& l,
293 const variable& new_val,
294 const std::size_t num,
295 const mutable_map_substitution<>& substs);
296 match_tree build_tree(build_pars pars, std::size_t i);
297 match_tree create_tree(
const data_equation_list& rules);
299 void thread_initialise()
301 mCRL2log(mcrl2::log::debug) <<
"Initialise busy/forbidden flags\n";
302 m_thread_aterm_pool = &atermpp::detail::g_thread_term_pool();
306struct rewriter_interface
308 std::string caller_toolset_version;
310 RewriterCompilingJitty* rewriter;
311 void (*rewrite_external)(data_expression& result,
const data_expression& t, RewriterCompilingJitty*);
312 void (*rewrite_cleanup)();