22#include <spot/twa/twagraph.hh>
23#include <spot/twaalgos/emptiness.hh>
24#include <spot/misc/bitvect.hh>
66 template <
typename Iterator>
67 bool operator()(Iterator, Iterator)
const noexcept
78 const std::vector<unsigned>& sccof_;
79 unsigned desired_scc_;
81 keep_inner_scc(
const std::vector<unsigned>& sccof,
unsigned desired_scc)
82 : sccof_(sccof), desired_scc_(desired_scc)
86 template <
typename Iterator>
87 bool operator()(Iterator begin, Iterator end)
const noexcept
91 if (sccof_[*begin++] == desired_scc_)
100 template <
typename Graph,
typename Filter>
101 class SPOT_API scc_edge_iterator
104 typedef typename std::conditional<std::is_const<Graph>::value,
105 const typename Graph::edge_storage_t,
106 typename Graph::edge_storage_t>::type
108 typedef value_type& reference;
109 typedef value_type* pointer;
110 typedef std::ptrdiff_t difference_type;
111 typedef std::forward_iterator_tag iterator_category;
113 typedef std::vector<unsigned>::const_iterator state_iterator;
115 typedef typename std::conditional<std::is_const<Graph>::value,
116 const typename Graph::edge_vector_t,
117 typename Graph::edge_vector_t>::type
120 typedef typename std::conditional<std::is_const<Graph>::value,
121 const typename Graph::state_vector,
122 typename Graph::state_vector>::type
124 typedef const typename Graph::dests_vector_t dv_t;
139 void inc_state_maybe_()
141 while (!t_ && (++pos_ != end_))
142 t_ = (*sv_)[*pos_].succ;
147 t_ = (*tv_)[t_].next_succ;
152 bool ignore_current()
154 unsigned dst = (*this)->dst;
158 if (!filt_(&(*this)->dst, 1 + &(*this)->dst))
161 return efilter_((*tv_)[t_], dst, efilter_data_)
162 != edge_filter_choice::keep;
168 const unsigned* d = dv_->data() + ~dst;
169 if (!filt_(d + 1, d + *d + 1))
175 const unsigned* end = d + *d + 1;
176 for (
const unsigned* i = d + 1; i != end; ++i)
178 if (efilter_((*tv_)[t_], *i, efilter_data_)
179 == edge_filter_choice::keep)
189 scc_edge_iterator(state_iterator begin, state_iterator end,
190 tv_t* tv, sv_t* sv, dv_t* dv, Filter filt,
192 : pos_(begin), end_(end), t_(0), tv_(tv), sv_(sv), dv_(dv), filt_(filt),
193 efilter_(efilter), efilter_data_(efilter_data)
198 t_ = (*sv_)[*pos_].succ;
200 while (pos_ != end_ && ignore_current())
204 scc_edge_iterator& operator++()
208 while (pos_ != end_ && ignore_current());
212 scc_edge_iterator operator++(
int)
214 scc_edge_iterator old = *
this;
221 return pos_ == o.pos_ && t_ == o.t_;
226 return pos_ != o.pos_ || t_ != o.t_;
229 reference operator*()
const
234 pointer operator->()
const
241 template <
typename Graph,
typename Filter>
242 class SPOT_API scc_edges
245 typedef scc_edge_iterator<Graph, Filter> iter_t;
246 typedef typename iter_t::tv_t tv_t;
247 typedef typename iter_t::sv_t sv_t;
248 typedef typename iter_t::dv_t dv_t;
249 typedef typename iter_t::state_iterator state_iterator;
251 state_iterator begin_;
261 scc_edges(state_iterator begin, state_iterator end,
262 tv_t* tv, sv_t* sv, dv_t* dv, Filter filt,
264 : begin_(begin), end_(end), tv_(tv), sv_(sv), dv_(dv), filt_(filt),
265 efilter_(efilter), efilter_data_(efilter_data)
271 return {begin_, end_, tv_, sv_, dv_, filt_, efilter_, efilter_data_};
276 return {end_, end_,
nullptr,
nullptr,
nullptr, filt_,
nullptr,
nullptr};
303 acc_({}), trivial_(
true), accepting_(
false),
304 rejecting_(
false), useful_(
false)
311 : acc_(acc), common_(common),
312 trivial_(trivial), accepting_(
false),
313 rejecting_(
false), useful_(
false)
362 const std::vector<unsigned>&
states()
const
429 typedef std::underlying_type_t<scc_info_options> ut;
431 &
static_cast<ut
>(right));
439 typedef std::underlying_type_t<scc_info_options> ut;
441 |
static_cast<ut
>(right));
444 class SPOT_API scc_and_mark_filter;
484 int one_acc_scc_ = -1;
499 [[noreturn]]
static void report_need_track_states();
500 [[noreturn]]
static void report_need_track_succs();
501 [[noreturn]]
static void report_incompatible_stop_on_acc();
510 unsigned initial_state = ~0U,
512 void* filter_data =
nullptr,
516 :
scc_info(aut, ~0
U, nullptr, nullptr, options)
584 return scc_of(st) != -1U;
594 std::vector<scc_node>::const_iterator
begin()
const
596 return node_.begin();
600 std::vector<scc_node>::const_iterator
end()
const
606 std::vector<scc_node>::const_iterator
cbegin()
const
608 return node_.cbegin();
612 std::vector<scc_node>::const_iterator
cend()
const
618 std::vector<scc_node>::const_reverse_iterator
rbegin()
const
620 return node_.rbegin();
624 std::vector<scc_node>::const_reverse_iterator
rend()
const
630 const std::vector<unsigned>&
states_of(
unsigned scc)
const
632 if (SPOT_UNLIKELY(!(options_ & scc_info_options::TRACK_STATES)))
633 report_need_track_states();
634 return node(scc).states();
642 internal::scc_edges<const twa_graph::graph_t, internal::keep_all>
645 auto& states = states_of(scc);
646 return {states.begin(), states.end(),
647 &aut_->edge_vector(), &aut_->states(),
648 &aut_->get_graph().dests_vector(),
649 internal::keep_all(), filter_,
const_cast<void*
>(filter_data_)};
659 internal::scc_edges<const twa_graph::graph_t, internal::keep_inner_scc>
662 auto& states = states_of(scc);
663 return {states.begin(), states.end(),
664 &aut_->edge_vector(), &aut_->states(),
665 &aut_->get_graph().dests_vector(),
666 internal::keep_inner_scc(sccof_, scc), filter_,
667 const_cast<void*
>(filter_data_)};
673 return node(scc).one_state();
679 SPOT_ASSERT(filter_ || scc_count() - 1 == scc_of(initial_state_));
680 return scc_of(initial_state_);
686 if (SPOT_UNLIKELY(!(options_ & scc_info_options::TRACK_SUCCS)))
687 report_need_track_succs();
688 return node(scc).succ();
694 return node(scc).is_trivial();
700 return node(scc).is_accepting();
706 return node(scc).is_rejecting();
713 return aut_->acc().accepting(acc_sets_of(scc));
740 if (SPOT_UNLIKELY(!!(options_ & scc_info_options::STOP_ON_ACC)))
741 report_incompatible_stop_on_acc();
742 if (SPOT_UNLIKELY(!(options_ & scc_info_options::TRACK_SUCCS)))
743 report_need_track_succs();
744 return node(scc).is_useful();
750 return reachable_state(st) && is_useful_scc(scc_of(st));
755 std::vector<std::set<acc_cond::mark_t>>
marks()
const;
757 std::set<acc_cond::mark_t>
marks_of(
unsigned scc)
const;
764 return node(scc).acc_marks();
771 return node(scc).common_marks();
807 bool preserve_names =
false)
const;
815 std::vector<acc_cond::rs_pair>& pairs,
816 std::vector<unsigned>& res,
817 std::vector<unsigned>& old)
const;
823 std::vector<unsigned>
842 bool restore_old_acc_ =
false;
848 unsigned dst,
void* data);
857 unsigned dst,
void* data);
868 : lower_si_(&lower_si), lower_scc_(lower_scc), cut_sets_(cut_sets),
869 aut_(lower_si_->get_aut()), old_acc_(aut_->get_acceptance())
872 if (f == &filter_mark_
873 || f == &filter_scc_and_mark_
874 || f == &filter_scc_and_mark_and_edges_)
878 cut_sets_ |= d.cut_sets_;
879 if (f == &filter_scc_and_mark_and_edges_)
900 : lower_si_(nullptr), cut_sets_(cut_sets), aut_(aut),
901 old_acc_(aut_->get_acceptance())
907 restore_acceptance();
913 std::const_pointer_cast<twa_graph>(aut_)->set_acceptance(new_acc);
914 restore_old_acc_ =
true;
920 if (!restore_old_acc_)
922 std::const_pointer_cast<twa_graph>(aut_)->set_acceptance(old_acc_);
923 restore_old_acc_ =
false;
937 return aut_->get_init_state_number();
944 return filter_scc_and_mark_and_edges_;
946 return filter_scc_and_mark_;
956 SPOT_API std::ostream&
An acceptance condition.
Definition acc.hh:54
A bit vector.
Definition bitvect.hh:51
Create a filter for SCC and marks.
Definition sccinfo.hh:835
static scc_info::edge_filter_choice filter_scc_and_mark_(const twa_graph::edge_storage_t &e, unsigned dst, void *data)
Filter by SCC membership and cut sets.
acc_cond old_acc_
Saved acceptance for restoration.
Definition sccinfo.hh:841
void override_acceptance(const acc_cond &new_acc)
Temporarily override the automaton's acceptance condition.
Definition sccinfo.hh:911
unsigned lower_scc_
SCC number in lower_si_ to restrict to.
Definition sccinfo.hh:838
static scc_info::edge_filter_choice filter_scc_and_mark_and_edges_(const twa_graph::edge_storage_t &e, unsigned dst, void *data)
Filter by SCC, marks, and edge set.
const_twa_graph_ptr aut_
The automaton being filtered.
Definition sccinfo.hh:840
scc_and_mark_filter(const const_twa_graph_ptr &aut, acc_cond::mark_t cut_sets)
Specify how to restrict scc_info to some acceptance sets.
Definition sccinfo.hh:898
scc_and_mark_filter(const scc_info &lower_si, unsigned lower_scc, acc_cond::mark_t cut_sets, const bitvect &keep)
Construct with an additional bitvect of edges to keep.
Definition sccinfo.hh:885
const scc_info * lower_si_
The original scc_info used to filter.
Definition sccinfo.hh:837
const_twa_graph_ptr get_aut() const
Return the filtered automaton.
Definition sccinfo.hh:927
void restore_acceptance()
Restore the original acceptance condition.
Definition sccinfo.hh:918
scc_and_mark_filter(const scc_info &lower_si, unsigned lower_scc, acc_cond::mark_t cut_sets)
Specify how to restrict scc_info to some SCC and acceptance sets.
Definition sccinfo.hh:865
unsigned start_state() const
Return the starting state for scc_info exploration.
Definition sccinfo.hh:933
acc_cond::mark_t cut_sets_
Acceptance sets treated as cut edges.
Definition sccinfo.hh:839
static scc_info::edge_filter_choice filter_mark_(const twa_graph::edge_storage_t &e, unsigned, void *data)
Filter by acceptance marks only.
scc_info::edge_filter get_filter() const
Return the appropriate edge filter function.
Definition sccinfo.hh:941
Storage for SCC related information.
Definition sccinfo.hh:285
acc_cond::mark_t acc_marks() const
Return the union of all acceptance marks in this SCC.
Definition sccinfo.hh:350
bool is_rejecting() const
True if we know that all cycles in the SCC are rejecting.
Definition sccinfo.hh:338
const std::vector< unsigned > & states() const
Return all states belonging to this SCC.
Definition sccinfo.hh:362
scc_succs succ_
Successor SCCs of this SCC.
Definition sccinfo.hh:291
bool rejecting_
True if the SCC is necessarily rejecting.
Definition sccinfo.hh:298
const scc_succs & succ() const
Return the list of successor SCC indices.
Definition sccinfo.hh:374
bool is_accepting() const
True if we know that the SCC has an accepting cycle.
Definition sccinfo.hh:328
bool accepting_
True if the SCC is necessarily accepting.
Definition sccinfo.hh:297
acc_cond::mark_t common_marks() const
Return the marks common to all transitions in this SCC.
Definition sccinfo.hh:356
scc_info_node(acc_cond::mark_t acc, acc_cond::mark_t common, bool trivial) noexcept
Construct an SCC node with given acceptance information.
Definition sccinfo.hh:309
unsigned one_state_
An arbitrary state in this SCC.
Definition sccinfo.hh:293
unsigned one_state() const
Return one arbitrary state in this SCC.
Definition sccinfo.hh:368
acc_cond::mark_t acc_
Union of acceptance marks seen.
Definition sccinfo.hh:294
bool trivial_
True if the SCC has no cycle.
Definition sccinfo.hh:296
bool useful_
True if the SCC can reach an accepting SCC.
Definition sccinfo.hh:299
std::vector< unsigned > states_
States of the component.
Definition sccinfo.hh:292
scc_info_node() noexcept
Default-construct an empty trivial SCC node.
Definition sccinfo.hh:302
acc_cond::mark_t common_
Marks common to all edges.
Definition sccinfo.hh:295
bool is_trivial() const
True if the SCC has no cycle.
Definition sccinfo.hh:318
std::vector< unsigned > scc_succs
List of successor SCC indices.
Definition sccinfo.hh:288
bool is_useful() const
True if the SCC can reach an accepting SCC.
Definition sccinfo.hh:344
Compute an SCC map and gather assorted information.
Definition sccinfo.hh:465
scc_info(const_twa_graph_ptr aut, scc_info_options options)
Create the scc_info map for aut.
Definition sccinfo.hh:515
bool is_maximally_accepting_scc(unsigned scc) const
Whether a cycle going through all edges of the SCC is accepting.
Definition sccinfo.hh:711
std::vector< std::set< acc_cond::mark_t > > marks() const
Returns, for each accepting SCC, the set of all marks appearing in it.
std::vector< unsigned > sccof_
SCC number for each state.
Definition sccinfo.hh:478
int one_accepting_scc() const
Return the number of one accepting SCC if any, -1 otherwise.
Definition sccinfo.hh:576
unsigned scc_count() const
Return the total number of SCCs.
Definition sccinfo.hh:563
bdd scc_ap_support(unsigned scc) const
Return the APs that appear in SCC scc.
unsigned initial() const
Get number of the SCC containing the initial state.
Definition sccinfo.hh:677
unsigned scc_of(unsigned st) const
Return the SCC number containing state st.
Definition sccinfo.hh:588
void determine_usefulness()
Update the useful_ bits for all SCC nodes.
internal::scc_edges< const twa_graph::graph_t, internal::keep_inner_scc > inner_edges_of(unsigned scc) const
A fake container to iterate over all edges between states of an SCC.
Definition sccinfo.hh:660
edge_filter filter_
Optional edge filter function.
Definition sccinfo.hh:482
unsigned one_state_of(unsigned scc) const
Return one arbitrary state in SCC scc.
Definition sccinfo.hh:671
bool is_rejecting_scc(unsigned scc) const
True if SCC scc is necessarily rejecting.
Definition sccinfo.hh:704
const_twa_graph_ptr aut_
The automaton being analyzed.
Definition sccinfo.hh:480
void * get_filter_data() const
Return the user data passed to the edge filter.
Definition sccinfo.hh:557
bool is_useful_state(unsigned st) const
True if state st belongs to a useful SCC.
Definition sccinfo.hh:748
bool check_scc_emptiness(unsigned n) const
Recompute whether an SCC is accepting or not.
const scc_node & node(unsigned scc) const
Return the SCC node for the given SCC index.
Definition sccinfo.hh:492
std::set< acc_cond::mark_t > marks_of(unsigned scc) const
Return the set of all marks appearing in SCC scc.
bool is_trivial(unsigned scc) const
True if SCC scc has no cycle.
Definition sccinfo.hh:692
const_twa_graph_ptr get_aut() const
Return the automaton passed to the constructor.
Definition sccinfo.hh:539
bool is_accepting_scc(unsigned scc) const
True if SCC scc is necessarily accepting.
Definition sccinfo.hh:698
std::vector< scc_node >::const_iterator cbegin() const
Const iterator to the first SCC node.
Definition sccinfo.hh:606
void determine_unknown_acceptance()
Study the SCCs that are currently reported neither as accepting nor as rejecting because of the prese...
void get_accepting_run(unsigned scc, twa_run_ptr r) const
Retrieves an accepting run of the automaton whose cycle is in the SCC.
spot::edge_filter_choice edge_filter_choice
Imported type.
Definition sccinfo.hh:473
const std::vector< unsigned > & states_of(unsigned scc) const
Return all states belonging to SCC scc.
Definition sccinfo.hh:630
std::vector< scc_node >::const_iterator end() const
Past-the-end iterator over SCC nodes.
Definition sccinfo.hh:600
scc_info(const_twa_graph_ptr aut, unsigned initial_state=~0U, edge_filter filter=nullptr, void *filter_data=nullptr, scc_info_options options=scc_info_options::ALL)
Create the scc_info map for aut.
scc_info(const scc_and_mark_filter &filt)
Create an scc_info map from some filter.
Definition sccinfo.hh:532
std::vector< unsigned > states_on_acc_cycle_of(unsigned scc) const
: Get all states visited by any accepting cycles of the 'scc'.
bool reachable_state(unsigned st) const
True if state st is reachable from the initial state.
Definition sccinfo.hh:582
void states_on_acc_cycle_of_rec(unsigned scc, acc_cond::mark_t all_fin, acc_cond::mark_t all_inf, unsigned nb_pairs, std::vector< acc_cond::rs_pair > &pairs, std::vector< unsigned > &res, std::vector< unsigned > &old) const
: Recursive function used by states_on_acc_cycle_of().
std::vector< scc_node >::const_iterator begin() const
Iterator to the first SCC node.
Definition sccinfo.hh:594
scc_info_options get_options() const
Return the options used during construction.
Definition sccinfo.hh:545
scc_info_node scc_node
Alias for scc_info_node.
Definition sccinfo.hh:469
std::vector< scc_node > node_
SCC nodes in reverse topological order.
Definition sccinfo.hh:479
std::vector< scc_node >::const_reverse_iterator rbegin() const
Reverse iterator to the last SCC node.
Definition sccinfo.hh:618
acc_cond::mark_t common_sets_of(unsigned scc) const
Definition sccinfo.hh:769
std::vector< scc_node >::const_reverse_iterator rend() const
Reverse past-the-end iterator over SCC nodes.
Definition sccinfo.hh:624
void * filter_data_
User data passed to the edge filter.
Definition sccinfo.hh:483
internal::scc_edges< const twa_graph::graph_t, internal::keep_all > edges_of(unsigned scc) const
A fake container to iterate over all edges leaving any state of an SCC.
Definition sccinfo.hh:643
edge_filter get_filter() const
Return the edge filter function.
Definition sccinfo.hh:551
unsigned initial_state_
Initial state of the automaton.
Definition sccinfo.hh:481
scc_info_options options_
Options used during construction.
Definition sccinfo.hh:485
std::vector< scc_node >::const_iterator cend() const
Const past-the-end iterator over SCC nodes.
Definition sccinfo.hh:612
bool is_useful_scc(unsigned scc) const
True if SCC scc can reach an accepting SCC.
Definition sccinfo.hh:738
spot::edge_filter edge_filter
Imported edge filter type.
Definition sccinfo.hh:474
acc_cond::mark_t acc_sets_of(unsigned scc) const
Returns, for a given SCC, the set of all colors appearing in it. It is the set of colors that appear ...
Definition sccinfo.hh:762
scc_info_node::scc_succs scc_succs
Successor SCC list.
Definition sccinfo.hh:470
const scc_succs & succ(unsigned scc) const
Return the successor SCCs of SCC scc.
Definition sccinfo.hh:684
scc_info(const scc_and_mark_filter &filt, scc_info_options options)
Create an scc_info map from some filter.
std::vector< twa_graph_ptr > split_on_sets(unsigned scc, acc_cond::mark_t sets, bool preserve_names=false) const
Split an SCC into multiple automata separated by some acceptance sets.
std::vector< bool > weak_sccs() const
Return a vector indicating which SCCs are weak.
spot::internal::edge_storage< unsigned, unsigned, unsigned, internal::boxed_label< twa_graph_edge_data, false > > edge_storage_t
Edge storage type (src, dst, and edge data).
Definition twagraph.hh:218
scc_info_options operator&(scc_info_options left, scc_info_options right)
Bitwise AND of two scc_info_options values.
Definition sccinfo.hh:427
bool operator!(scc_info_options me)
Test if an scc_info_options value equals NONE.
Definition sccinfo.hh:419
std::shared_ptr< twa_run > twa_run_ptr
Shared pointer to a twa_run.
Definition twa.hh:41
edge_filter_choice(* edge_filter)(const twa_graph::edge_storage_t &e, unsigned dst, void *filter_data)
An edge_filter may be called on each edge to decide what to do with it.
Definition sccinfo.hh:58
scc_info_options
Options to alter the behavior of scc_info.
Definition sccinfo.hh:383
edge_filter_choice
An edge_filter may be called on each edge to decide what to do with it.
Definition sccinfo.hh:56
@ TRACK_STATES_IF_FIN_USED
@ ALL
Default behavior: explore everything and track states and succs.
@ PROCESS_UNREACHABLE_STATES
std::shared_ptr< const twa_graph > const_twa_graph_ptr
Shared pointer to a const twa_graph.
Definition fwd.hh:41
Definition automata.hh:26
std::ostream & dump_scc_info_dot(std::ostream &out, const_twa_graph_ptr aut, scc_info *sccinfo=nullptr)
Dump the SCC graph of aut on out.
constexpr bool operator==(trival a, trival b)
Equality comparison of two trival values.
Definition trival.hh:134
const mc_rvalue operator|(const mc_rvalue &lhs, const mc_rvalue &rhs)
This function helps to find the output value from a set of threads that may have different values.
Definition mc.hh:140
constexpr bool operator!=(trival a, trival b)
Inequality comparison of two trival values.
Definition trival.hh:140
An acceptance mark.
Definition acc.hh:76