Use shared_ptr for the emptiness check interfaces.

At the same time, this adds a is_empty() method to the tgba class,
simplifying many places that ran emptiness checks.

* iface/dve2/dve2check.cc, src/bin/ltlcross.cc,
src/dstarparse/dra2ba.cc, src/ltlvisit/contain.cc, src/tgba/tgba.cc,
src/tgba/tgba.hh, src/tgbaalgos/emptiness.cc,
src/tgbaalgos/emptiness.hh, src/tgbaalgos/gtec/ce.cc,
src/tgbaalgos/gtec/ce.hh, src/tgbaalgos/gtec/gtec.cc,
src/tgbaalgos/gtec/gtec.hh, src/tgbaalgos/gv04.cc,
src/tgbaalgos/gv04.hh, src/tgbaalgos/magic.cc,
src/tgbaalgos/magic.hh, src/tgbaalgos/minimize.cc,
src/tgbaalgos/ndfs_result.hxx, src/tgbaalgos/powerset.cc,
src/tgbaalgos/projrun.cc, src/tgbaalgos/projrun.hh,
src/tgbaalgos/reducerun.cc, src/tgbaalgos/reducerun.hh,
src/tgbaalgos/replayrun.cc, src/tgbaalgos/replayrun.hh,
src/tgbaalgos/rundotdec.cc, src/tgbaalgos/rundotdec.hh,
src/tgbaalgos/se05.cc, src/tgbaalgos/se05.hh,
src/tgbaalgos/tau03.cc, src/tgbaalgos/tau03.hh,
src/tgbaalgos/tau03opt.cc, src/tgbaalgos/tau03opt.hh,
src/tgbaalgos/word.cc, src/tgbaalgos/word.hh,
src/tgbatest/checkpsl.cc, src/tgbatest/complementation.cc,
src/tgbatest/emptchk.cc, src/tgbatest/ltl2tgba.cc,
src/tgbatest/randtgba.cc, wrap/python/ajax/spot.in,
wrap/python/spot.i: Use shared_ptr.
This commit is contained in:
Alexandre Duret-Lutz 2014-08-23 18:34:00 +02:00
parent 803e17bb8d
commit 6d7c258fd7
42 changed files with 335 additions and 402 deletions

View file

@ -157,16 +157,16 @@ checked_main(int argc, char **argv)
spot::ltl::atomic_prop_set ap;
auto dict = spot::make_bdd_dict();
spot::const_kripke_ptr model = 0;
spot::const_tgba_ptr prop = 0;
spot::const_tgba_ptr product = 0;
spot::emptiness_check_instantiator* echeck_inst = 0;
spot::const_kripke_ptr model = nullptr;
spot::const_tgba_ptr prop = nullptr;
spot::const_tgba_ptr product = nullptr;
spot::emptiness_check_instantiator_ptr echeck_inst = nullptr;
int exit_code = 0;
spot::postprocessor post;
const spot::ltl::formula* deadf = 0;
const spot::ltl::formula* f = 0;
const spot::ltl::formula* deadf = nullptr;
const spot::ltl::formula* f = nullptr;
if (dead == 0 || !strcasecmp(dead, "true"))
if (!dead || !strcasecmp(dead, "true"))
{
deadf = spot::ltl::constant::true_instance();
}
@ -182,8 +182,7 @@ checked_main(int argc, char **argv)
if (output == EmptinessCheck)
{
const char* err;
echeck_inst =
spot::emptiness_check_instantiator::construct(echeck_algo, &err);
echeck_inst = spot::make_emptiness_check_instantiator(echeck_algo, &err);
if (!echeck_inst)
{
std::cerr << "Failed to parse argument of -e/-E near `"
@ -265,14 +264,14 @@ checked_main(int argc, char **argv)
assert(echeck_inst);
{
spot::emptiness_check* ec = echeck_inst->instantiate(product);
auto ec = echeck_inst->instantiate(product);
bool search_many = echeck_inst->options().get("repeated");
assert(ec);
do
{
int memused = spot::memusage();
tm.start("running emptiness check");
spot::emptiness_check_result* res;
spot::emptiness_check_result_ptr res;
try
{
res = ec->check();
@ -315,7 +314,7 @@ checked_main(int argc, char **argv)
else if (accepting_run)
{
spot::tgba_run* run;
spot::tgba_run_ptr run;
tm.start("computing accepting run");
try
{
@ -337,31 +336,24 @@ checked_main(int argc, char **argv)
else
{
tm.start("reducing accepting run");
spot::tgba_run* redrun =
spot::reduce_run(res->automaton(), run);
run = spot::reduce_run(res->automaton(), run);
tm.stop("reducing accepting run");
delete run;
run = redrun;
tm.start("printing accepting run");
spot::print_tgba_run(std::cout, product, run);
tm.stop("printing accepting run");
}
delete run;
}
else
{
std::cout << "an accepting run exists "
<< "(use -C to print it)" << std::endl;
}
delete res;
}
while (search_many);
delete ec;
}
safe_exit:
delete echeck_inst;
if (f)
f->destroy();

View file

@ -1071,9 +1071,7 @@ namespace
size_t i, size_t j, bool icomp, bool jcomp)
{
auto prod = spot::product(aut_i, aut_j);
spot::emptiness_check* ec = spot::couvreur99(prod);
spot::emptiness_check_result* res = ec->check();
auto res = spot::couvreur99(prod)->check();
if (res)
{
std::ostream& err = global_error();
@ -1088,17 +1086,15 @@ namespace
err << "*N" << j;
err << " is nonempty";
spot::tgba_run* run = res->accepting_run();
auto run = res->accepting_run();
if (run)
{
const spot::tgba_run* runmin = reduce_run(prod, run);
delete run;
run = reduce_run(prod, run);
std::cerr << "; both automata accept the infinite word\n"
<< " ";
spot::tgba_word w(runmin);
spot::tgba_word w(run);
w.simplify();
w.print(example(), prod->get_dict()) << '\n';
delete runmin;
}
else
{
@ -1106,9 +1102,7 @@ namespace
}
end_error();
}
delete res;
delete ec;
return res;
return !!res;
}
static bool

View file

@ -148,18 +148,10 @@ namespace spot
{
state_set keep(sl.begin(), sl.end());
auto masked = build_tgba_mask_keep(dra->aut, keep, sl.front());
emptiness_check* ec = couvreur99(nra_to_nba(dra, masked));
emptiness_check_result* ecr = ec->check();
delete ecr;
delete ec;
if (ecr)
{
if (!nra_to_nba(dra, masked)->is_empty())
// This SCC is not DBA-realizable.
//std::cerr << "not DBA-realizable\n";
return false;
}
}
//std::cerr << "non-accepting\n";
for (state_list::const_iterator i = sl.begin();
i != sl.end(); ++i)
nonfinal.push_back(*i);

View file

@ -69,21 +69,10 @@ namespace spot
if (i != l->incompatible.end())
return i->second;
auto ec = couvreur99(product(l->translation, g->translation));
auto ecr = ec->check();
if (!ecr)
{
l->incompatible[g] = true;
g->incompatible[l] = true;
}
else
{
l->incompatible[g] = false;
g->incompatible[l] = false;
delete ecr;
}
delete ec;
return !ecr;
bool res = product(l->translation, g->translation)->is_empty();
l->incompatible[g] = res;
g->incompatible[l] = res;
return res;
}

View file

@ -21,6 +21,7 @@
// along with this program. If not, see <http://www.gnu.org/licenses/>.
#include "tgba.hh"
#include "tgbaalgos/gtec/gtec.hh"
namespace spot
{
@ -85,4 +86,13 @@ namespace spot
return num_acc_;
}
bool
tgba::is_empty() const
{
// FIXME: This should be improved based on properties of the
// automaton. For instance we do not need couvreur99 is we know
// the automaton is weak.
return !couvreur99(shared_from_this())->check();
}
}

View file

@ -27,7 +27,6 @@
#include "fwd.hh"
#include <cassert>
#include <memory>
#include <memory>
#include "misc/casts.hh"
#include "misc/hash.hh"
@ -465,7 +464,7 @@ namespace spot
/// we never represent transitions! Transition informations are
/// obtained by querying the iterator over the successors of
/// a state.
class SPOT_API tgba
class SPOT_API tgba: public std::enable_shared_from_this<tgba>
{
protected:
tgba();
@ -641,6 +640,8 @@ namespace spot
/// the other operand.
virtual bdd neg_acceptance_conditions() const = 0;
virtual bool is_empty() const;
protected:
/// Do the actual computation of tgba::support_conditions().
virtual bdd compute_support_conditions(const state* state) const = 0;

View file

@ -77,8 +77,8 @@ namespace spot
std::ostream&
print_tgba_run(std::ostream& os,
const_tgba_ptr a,
const tgba_run* run)
const const_tgba_ptr& a,
const const_tgba_run_ptr& run)
{
bdd_dict_ptr d = a->get_dict();
os << "Prefix:" << std::endl;
@ -109,10 +109,10 @@ namespace spot
// emptiness_check_result
//////////////////////////////////////////////////////////////////////
tgba_run*
tgba_run_ptr
emptiness_check_result::accepting_run()
{
return 0;
return nullptr;
}
const unsigned_statistics*
@ -149,6 +149,12 @@ namespace spot
return dynamic_cast<const unsigned_statistics*>(this);
}
const ec_statistics*
emptiness_check::emptiness_check_statistics() const
{
return dynamic_cast<const ec_statistics*>(this);
}
const char*
emptiness_check::parse_options(char* options)
{
@ -180,16 +186,10 @@ namespace spot
namespace
{
emptiness_check*
make_couvreur99(const const_tgba_ptr& a, spot::option_map o)
{
return couvreur99(a, o);
}
struct ec_algo
{
const char* name;
spot::emptiness_check* (*construct)(const const_tgba_ptr&,
emptiness_check_ptr(*construct)(const const_tgba_ptr&,
spot::option_map);
unsigned int min_acc;
unsigned int max_acc;
@ -197,12 +197,12 @@ namespace spot
ec_algo ec_algos[] =
{
{ "Cou99", make_couvreur99, 0, -1U },
{ "CVWY90", spot::magic_search, 0, 1 },
{ "GV04", spot::explicit_gv04_check, 0, 1 },
{ "SE05", spot::se05, 0, 1 },
{ "Tau03", spot::explicit_tau03_search, 1, -1U },
{ "Tau03_opt", spot::explicit_tau03_opt_search, 0, -1U },
{ "Cou99", couvreur99, 0, -1U },
{ "CVWY90", magic_search, 0, 1 },
{ "GV04", explicit_gv04_check, 0, 1 },
{ "SE05", se05, 0, 1 },
{ "Tau03", explicit_tau03_search, 1, -1U },
{ "Tau03_opt", explicit_tau03_opt_search, 0, -1U },
};
}
@ -224,14 +224,14 @@ namespace spot
return static_cast<ec_algo*>(info_)->max_acc;
}
emptiness_check*
emptiness_check_ptr
emptiness_check_instantiator::instantiate(const const_tgba_ptr& a) const
{
return static_cast<ec_algo*>(info_)->construct(a, o_);
}
emptiness_check_instantiator*
emptiness_check_instantiator::construct(const char* name, const char** err)
emptiness_check_instantiator_ptr
make_emptiness_check_instantiator(const char* name, const char** err)
{
// Skip spaces.
while (*name && strchr(" \t\n", *name))
@ -272,17 +272,26 @@ namespace spot
if (n == info->name)
{
*err = 0;
return new emptiness_check_instantiator(o, info);
struct emptiness_check_instantiator_aux:
public emptiness_check_instantiator
{
emptiness_check_instantiator_aux(option_map o, void* i):
emptiness_check_instantiator(o, i)
{
}
};
return std::make_shared<emptiness_check_instantiator_aux>(o, info);
}
*err = name;
return 0;
return nullptr;
}
// tgba_run_to_tgba
//////////////////////////////////////////////////////////////////////
tgba_digraph_ptr
tgba_run_to_tgba(const const_tgba_ptr& a, const tgba_run* run)
tgba_run_to_tgba(const const_tgba_ptr& a, const const_tgba_run_ptr& run)
{
auto d = a->get_dict();
auto res = make_tgba_digraph(d);

View file

@ -34,6 +34,8 @@
namespace spot
{
struct tgba_run;
typedef std::shared_ptr<tgba_run> tgba_run_ptr;
typedef std::shared_ptr<const tgba_run> const_tgba_run_ptr;
/// \addtogroup emptiness_check Emptiness-checks
/// \ingroup tgba_algorithms
@ -99,7 +101,7 @@ namespace spot
/// cannot produce a counter example (that does not mean there
/// is no counter-example; the mere existence of an instance of
/// this class asserts the existence of a counter-example).
virtual tgba_run* accepting_run();
virtual tgba_run_ptr accepting_run();
/// The automaton on which an accepting_run() was found.
const const_tgba_ptr&
@ -129,8 +131,11 @@ namespace spot
option_map o_; ///< The options.
};
typedef std::shared_ptr<emptiness_check_result> emptiness_check_result_ptr;
/// Common interface to emptiness check algorithms.
class SPOT_API emptiness_check
class SPOT_API emptiness_check:
public std::enable_shared_from_this<emptiness_check>
{
public:
emptiness_check(const const_tgba_ptr& a, option_map o = option_map())
@ -173,11 +178,14 @@ namespace spot
/// Some emptiness_check algorithms, especially those using bit state
/// hashing may return 0 even if the automaton is not empty.
/// \see safe()
virtual emptiness_check_result* check() = 0;
virtual emptiness_check_result_ptr check() = 0;
/// Return statistics, if available.
virtual const unsigned_statistics* statistics() const;
/// Return emptiness check statistics, if available.
virtual const ec_statistics* emptiness_check_statistics() const;
/// Print statistics, if any.
virtual std::ostream& print_stats(std::ostream& os) const;
@ -189,25 +197,18 @@ namespace spot
option_map o_; ///< The options
};
typedef std::shared_ptr<emptiness_check> emptiness_check_ptr;
class emptiness_check_instantiator;
typedef std::shared_ptr<emptiness_check_instantiator>
emptiness_check_instantiator_ptr;
// Dynamically create emptiness checks. Given their name and options.
class SPOT_API emptiness_check_instantiator
{
public:
/// \brief Create an emptiness-check instantiator, given the name
/// of an emptiness check.
///
/// \a name should have the form \c "name" or \c "name(options)".
///
/// On error, the function returns 0. If the name of the algorithm
/// was unknown, \c *err will be set to \c name. If some fragment of
/// the options could not be parsed, \c *err will point to that
/// fragment.
static emptiness_check_instantiator* construct(const char* name,
const char** err);
/// Actually instantiate the emptiness check, for \a a.
emptiness_check* instantiate(const const_tgba_ptr& a) const;
emptiness_check_ptr instantiate(const const_tgba_ptr& a) const;
/// Accessor to the options.
/// @{
@ -233,15 +234,27 @@ namespace spot
///
/// \return \c -1U if no upper bound exists.
unsigned int max_acceptance_conditions() const;
private:
protected:
emptiness_check_instantiator(option_map o, void* i);
option_map o_;
void *info_;
};
/// @}
/// \brief Create an emptiness-check instantiator, given the name
/// of an emptiness check.
///
/// \a name should have the form \c "name" or \c "name(options)".
///
/// On error, the function returns 0. If the name of the algorithm
/// was unknown, \c *err will be set to \c name. If some fragment of
/// the options could not be parsed, \c *err will point to that
/// fragment.
SPOT_API emptiness_check_instantiator_ptr
make_emptiness_check_instantiator(const char* name, const char** err);
/// \addtogroup emptiness_check_algorithms Emptiness-check algorithms
/// \ingroup emptiness_check
@ -287,14 +300,16 @@ namespace spot
/// actually exists in the automaton (and will also display any
/// transition annotation).
SPOT_API std::ostream&
print_tgba_run(std::ostream& os, const_tgba_ptr a, const tgba_run* run);
print_tgba_run(std::ostream& os,
const const_tgba_ptr& a,
const const_tgba_run_ptr& run);
/// \brief Return an explicit_tgba corresponding to \a run (i.e. comparable
/// states are merged).
///
/// \pre \a run must correspond to an actual run of the automaton \a a.
SPOT_API tgba_digraph_ptr
tgba_run_to_tgba(const const_tgba_ptr& a, const tgba_run* run);
tgba_run_to_tgba(const const_tgba_ptr& a, const const_tgba_run_ptr& run);
/// @}

View file

@ -32,7 +32,7 @@ namespace spot
{
public:
shortest_path(const state_set* t,
const couvreur99_check_status* ecs,
const std::shared_ptr<const couvreur99_check_status>& ecs,
couvreur99_check_result* r)
: bfs_steps(ecs->aut), target(t), ecs(ecs), r(r)
{
@ -68,13 +68,14 @@ namespace spot
private:
state_set seen;
const state_set* target;
const couvreur99_check_status* ecs;
std::shared_ptr<const couvreur99_check_status> ecs;
couvreur99_check_result* r;
};
}
couvreur99_check_result::couvreur99_check_result
(const couvreur99_check_status* ecs, option_map o)
(const std::shared_ptr<const couvreur99_check_status>& ecs,
option_map o)
: emptiness_check_result(ecs->aut, o), ecs_(ecs)
{
}
@ -90,10 +91,10 @@ namespace spot
return count;
}
tgba_run*
tgba_run_ptr
couvreur99_check_result::accepting_run()
{
run_ = new tgba_run;
run_ = std::make_shared<tgba_run>();
assert(!ecs_->root.empty());
@ -212,7 +213,7 @@ namespace spot
return false;
}
} b(ecs_, this, acc_to_traverse);
} b(ecs_.get(), this, acc_to_traverse);
substart = b.search(substart, run_->cycle);
assert(substart);

View file

@ -1,5 +1,5 @@
// -*- coding: utf-8 -*-
// Copyright (C) 2013 Laboratoire de Recherche et Développement de
// Copyright (C) 2013, 2014 Laboratoire de Recherche et Développement de
// l'Epita (LRDE).
// Copyright (C) 2004, 2005 Laboratoire d'Informatique de Paris 6 (LIP6),
// département Systèmes Répartis Coopératifs (SRC), Université Pierre
@ -35,10 +35,11 @@ namespace spot
public acss_statistics
{
public:
couvreur99_check_result(const couvreur99_check_status* ecs,
couvreur99_check_result(const
std::shared_ptr<const couvreur99_check_status>& ecs,
option_map o = option_map());
virtual tgba_run* accepting_run();
virtual tgba_run_ptr accepting_run();
void print_stats(std::ostream& os) const;
@ -50,8 +51,8 @@ namespace spot
void accepting_cycle();
private:
const couvreur99_check_status* ecs_;
tgba_run* run_;
std::shared_ptr<const couvreur99_check_status> ecs_;
tgba_run_ptr run_;
};
}

View file

@ -45,7 +45,7 @@ namespace spot
removed_components(0)
{
poprem_ = o.get("poprem", 1);
ecs_ = new couvreur99_check_status(a);
ecs_ = std::make_shared<couvreur99_check_status>(a);
stats["removed components"] =
static_cast<spot::unsigned_statistics::unsigned_fun>
(&couvreur99_check::get_removed_components);
@ -56,7 +56,6 @@ namespace spot
couvreur99_check::~couvreur99_check()
{
delete ecs_;
}
unsigned
@ -129,7 +128,7 @@ namespace spot
}
}
emptiness_check_result*
emptiness_check_result_ptr
couvreur99_check::check()
{
// We use five main data in this algorithm:
@ -281,15 +280,15 @@ namespace spot
// cycle.
ecs_->cycle_seed = p.first->first;
set_states(ecs_->states());
return new couvreur99_check_result(ecs_, options());
return std::make_shared<couvreur99_check_result>(ecs_, options());
}
}
// This automaton recognizes no word.
set_states(ecs_->states());
return 0;
return nullptr;
}
const couvreur99_check_status*
std::shared_ptr<const couvreur99_check_status>
couvreur99_check::result() const
{
return ecs_;
@ -383,7 +382,7 @@ namespace spot
}
}
emptiness_check_result*
emptiness_check_result_ptr
couvreur99_check_shy::check()
{
// Position in the loop seeking known successors.
@ -418,7 +417,7 @@ namespace spot
// This automaton recognizes no word.
set_states(ecs_->states());
assert(poprem_ || depth() == 0);
return 0;
return nullptr;
}
pos = todo.back().q.begin();
@ -554,7 +553,7 @@ namespace spot
// We have found an accepting SCC. Clean up TODO.
clear_todo();
set_states(ecs_->states());
return new couvreur99_check_result(ecs_, options());
return std::make_shared<couvreur99_check_result>(ecs_, options());
}
// Group the pending successors of formed SCC if requested.
if (group_)
@ -592,12 +591,12 @@ namespace spot
}
}
emptiness_check*
emptiness_check_ptr
couvreur99(const const_tgba_ptr& a, option_map o)
{
if (o.get("shy"))
return new couvreur99_check_shy(a, o);
return new couvreur99_check(a, o);
return std::make_shared<couvreur99_check_shy>(a, o);
return std::make_shared<couvreur99_check>(a, o);
}
}

View file

@ -136,10 +136,10 @@ namespace spot
/// states that belong to the same SCC will be considered when
/// choosing a successor. Otherwise, only the successor of the
/// topmost state on the DFS stack are considered.
SPOT_API emptiness_check*
SPOT_API emptiness_check_ptr
couvreur99(const const_tgba_ptr& a, option_map options = option_map());
#ifndef SWIG
/// \brief An implementation of the Couvreur99 emptiness-check algorithm.
///
/// See the documentation for spot::couvreur99.
@ -150,7 +150,7 @@ namespace spot
virtual ~couvreur99_check();
/// Check whether the automaton's language is empty.
virtual emptiness_check_result* check();
virtual emptiness_check_result_ptr check();
virtual std::ostream& print_stats(std::ostream& os) const;
@ -162,10 +162,10 @@ namespace spot
/// This status should not be deleted, it is a pointer
/// to a member of this class that will be deleted when
/// the couvreur99 object is deleted.
const couvreur99_check_status* result() const;
std::shared_ptr<const couvreur99_check_status> result() const;
protected:
couvreur99_check_status* ecs_;
std::shared_ptr<couvreur99_check_status> ecs_;
/// \brief Remove a strongly component from the hash.
///
/// This function remove all accessible state from a given
@ -191,7 +191,7 @@ namespace spot
couvreur99_check_shy(const const_tgba_ptr& a, option_map o = option_map());
virtual ~couvreur99_check_shy();
virtual emptiness_check_result* check();
virtual emptiness_check_result_ptr check();
protected:
struct successor {
@ -239,7 +239,7 @@ namespace spot
// reprocess the successor states of SCC that have been merged.
bool group2_;
};
#endif
/// @}
}

View file

@ -91,7 +91,7 @@ namespace spot
}
}
virtual emptiness_check_result*
virtual emptiness_check_result_ptr
check()
{
top = dftop = -1;
@ -162,7 +162,7 @@ namespace spot
set_states(h.size());
}
if (violation)
return new result(*this);
return std::make_shared<result>(*this);
return 0;
}
@ -287,10 +287,10 @@ namespace spot
return s;
}
virtual tgba_run*
virtual tgba_run_ptr
accepting_run()
{
tgba_run* res = new tgba_run;
auto res = std::make_shared<tgba_run>();
update_lowlinks();
#ifdef TRACE
@ -409,9 +409,9 @@ namespace spot
} // anonymous
emptiness_check*
emptiness_check_ptr
explicit_gv04_check(const const_tgba_ptr& a, option_map o)
{
return new gv04(a, o);
return std::make_shared<gv04>(a, o);
}
}

View file

@ -25,11 +25,10 @@
# include "misc/optionmap.hh"
# include "tgba/fwd.hh"
# include "emptiness.hh"
namespace spot
{
class emptiness_check;
/// \brief Emptiness check based on Geldenhuys and Valmari's
/// TACAS'04 paper.
/// \ingroup emptiness_check_algorithms
@ -54,7 +53,7 @@ namespace spot
isbn = {3-540-21299-X}
}
\endverbatim */
SPOT_API emptiness_check*
SPOT_API emptiness_check_ptr
explicit_gv04_check(const const_tgba_ptr& a, option_map o = option_map());
}

View file

@ -88,8 +88,10 @@ namespace spot
/// check() can be called several times (until it returns a null
/// pointer) to enumerate all the visited accepting paths. The method
/// visits only a finite set of accepting paths.
virtual emptiness_check_result* check()
virtual emptiness_check_result_ptr check()
{
auto t = std::static_pointer_cast<magic_search_>
(this->emptiness_check::shared_from_this());
if (st_red.empty())
{
assert(st_blue.empty());
@ -98,19 +100,19 @@ namespace spot
h.add_new_state(s0, BLUE);
push(st_blue, s0, bddfalse, bddfalse);
if (dfs_blue())
return new magic_search_result(*this, options());
return std::make_shared<magic_search_result>(t, options());
}
else
{
h.pop_notify(st_red.front().s);
pop(st_red);
if (!st_red.empty() && dfs_red())
return new magic_search_result(*this, options());
return std::make_shared<magic_search_result>(t, options());
else
if (dfs_blue())
return new magic_search_result(*this, options());
return std::make_shared<magic_search_result>(t, options());
}
return 0;
return nullptr;
}
virtual std::ostream& print_stats(std::ostream &os) const
@ -325,25 +327,25 @@ namespace spot
public acss_statistics
{
public:
result_from_stack(magic_search_& ms)
: emptiness_check_result(ms.automaton()), ms_(ms)
result_from_stack(std::shared_ptr<magic_search_> ms)
: emptiness_check_result(ms->automaton()), ms_(ms)
{
}
virtual tgba_run* accepting_run()
virtual tgba_run_ptr accepting_run()
{
assert(!ms_.st_blue.empty());
assert(!ms_.st_red.empty());
assert(!ms_->st_blue.empty());
assert(!ms_->st_red.empty());
tgba_run* run = new tgba_run;
auto run = std::make_shared<tgba_run>();
typename stack_type::const_reverse_iterator i, j, end;
tgba_run::steps* l;
l = &run->prefix;
i = ms_.st_blue.rbegin();
end = ms_.st_blue.rend(); --end;
i = ms_->st_blue.rbegin();
end = ms_->st_blue.rend(); --end;
j = i; ++j;
for (; i != end; ++i, ++j)
{
@ -353,12 +355,12 @@ namespace spot
l = &run->cycle;
j = ms_.st_red.rbegin();
j = ms_->st_red.rbegin();
tgba_run::step s = { i->s->clone(), j->label, j->acc };
l->push_back(s);
i = j; ++j;
end = ms_.st_red.rend(); --end;
end = ms_->st_red.rend(); --end;
for (; i != end; ++i, ++j)
{
tgba_run::step s = { i->s->clone(), j->label, j->acc };
@ -373,7 +375,7 @@ namespace spot
return 0;
}
private:
magic_search_& ms_;
std::shared_ptr<magic_search_> ms_;
};
# define FROM_STACK "ar:from_stack"
@ -381,8 +383,9 @@ namespace spot
class magic_search_result: public emptiness_check_result
{
public:
magic_search_result(magic_search_& m, option_map o = option_map())
: emptiness_check_result(m.automaton(), o), ms(m)
magic_search_result(const std::shared_ptr<magic_search_>& m,
option_map o = option_map())
: emptiness_check_result(m->automaton(), o), ms(m)
{
if (options()[FROM_STACK])
computer = new result_from_stack(ms);
@ -409,7 +412,7 @@ namespace spot
delete computer;
}
virtual tgba_run* accepting_run()
virtual tgba_run_ptr accepting_run()
{
return computer->accepting_run();
}
@ -421,7 +424,7 @@ namespace spot
private:
emptiness_check_result* computer;
magic_search_& ms;
std::shared_ptr<magic_search_> ms;
};
};
@ -584,18 +587,20 @@ namespace spot
} // anonymous
emptiness_check* explicit_magic_search(const const_tgba_ptr& a, option_map o)
emptiness_check_ptr
explicit_magic_search(const const_tgba_ptr& a, option_map o)
{
return new magic_search_<explicit_magic_search_heap>(a, 0, o);
return std::make_shared<magic_search_<explicit_magic_search_heap>>(a, 0, o);
}
emptiness_check* bit_state_hashing_magic_search(const const_tgba_ptr& a,
emptiness_check_ptr
bit_state_hashing_magic_search(const const_tgba_ptr& a,
size_t size, option_map o)
{
return new magic_search_<bsh_magic_search_heap>(a, size, o);
return std::make_shared<magic_search_<bsh_magic_search_heap>>(a, size, o);
}
emptiness_check*
emptiness_check_ptr
magic_search(const const_tgba_ptr& a, option_map o)
{
size_t size = o.get("bsh");

View file

@ -26,11 +26,10 @@
#include <cstddef>
#include "tgba/fwd.hh"
#include "misc/optionmap.hh"
#include "emptiness.hh"
namespace spot
{
class emptiness_check;
/// \addtogroup emptiness_check_algorithms
/// @{
@ -97,7 +96,7 @@ namespace spot
///
/// \bug The name is misleading. Magic-search is the algorithm
/// from \c godefroid.93.pstv, not \c courcoubetis.92.fmsd.
SPOT_API emptiness_check*
SPOT_API emptiness_check_ptr
explicit_magic_search(const const_tgba_ptr& a,
option_map o = option_map());
@ -128,7 +127,7 @@ namespace spot
///
/// \sa spot::explicit_magic_search
///
SPOT_API emptiness_check*
SPOT_API emptiness_check_ptr
bit_state_hashing_magic_search(const const_tgba_ptr& a, size_t size,
option_map o = option_map());
@ -138,7 +137,7 @@ namespace spot
/// bit_state_hashing_magic_search() according to the \c "bsh" option
/// in the \c option_map. If \c "bsh" is set and non null, its value
/// is used as the size of the hash map.
SPOT_API emptiness_check*
SPOT_API emptiness_check_ptr
magic_search(const const_tgba_ptr& a, option_map o = option_map());
/// @}

View file

@ -260,13 +260,7 @@ namespace spot
// Contrustruct a product between
// LOOP_A, and ORIG_A starting in *IT.
// FIXME: This could be sped up a lot!
emptiness_check* ec = couvreur99(product_at(loop_a, orig_a,
loop_a_init, it));
emptiness_check_result* res = ec->check();
delete res;
delete ec;
if (res)
if (!product_at(loop_a, orig_a, loop_a_init, it)->is_empty())
{
accepting = true;
break;
@ -674,25 +668,15 @@ namespace spot
bool ok = false;
emptiness_check* ec = couvreur99(product(min_aut_f, aut_neg_f));
emptiness_check_result* res = ec->check();
if (!res)
if (product(min_aut_f, aut_neg_f)->is_empty())
{
delete ec;
// Complement the minimized WDBA.
auto neg_min_aut_f = wdba_complement(min_aut_f);
ec = couvreur99(product(aut_f, neg_min_aut_f));
res = ec->check();
if (!res)
{
if (product(aut_f, neg_min_aut_f)->is_empty())
// Finally, we are now sure that it was safe
// to minimize the automaton.
ok = true;
}
}
delete res;
delete ec;
if (ok)
return min_aut_f;

View file

@ -95,9 +95,9 @@ namespace spot
public stats_interface<ndfs_result<ndfs_search, heap>, heap::Has_Size>
{
public:
ndfs_result(const ndfs_search& ms)
: emptiness_check_result(ms.automaton()), ms_(ms),
h_(ms_.get_heap())
ndfs_result(const std::shared_ptr<ndfs_search>& ms)
: emptiness_check_result(ms->automaton()), ms_(ms),
h_(ms->get_heap())
{
}
@ -105,10 +105,10 @@ namespace spot
{
}
virtual tgba_run* accepting_run()
virtual tgba_run_ptr accepting_run()
{
const stack_type& stb = ms_.get_st_blue();
const stack_type& str = ms_.get_st_red();
const stack_type& stb = ms_->get_st_blue();
const stack_type& str = ms_->get_st_red();
assert(!stb.empty());
@ -195,7 +195,7 @@ namespace spot
assert(!acc_trans.empty());
tgba_run* run = new tgba_run;
auto run = std::make_shared<tgba_run>();
// construct run->cycle from acc_trans.
construct_cycle(run, acc_trans);
// construct run->prefix (a minimal path from the initial state to any
@ -214,7 +214,7 @@ namespace spot
}
private:
const ndfs_search& ms_;
std::shared_ptr<ndfs_search> ms_;
const heap& h_;
template <typename T, int n>
friend struct stats_interface;
@ -529,7 +529,7 @@ namespace spot
const heap& h;
};
void construct_cycle(tgba_run* run,
void construct_cycle(tgba_run_ptr run,
const accepting_transitions_list& acc_trans)
{
assert(!acc_trans.empty());
@ -616,7 +616,7 @@ namespace spot
}
}
void construct_prefix(tgba_run* run)
void construct_prefix(tgba_run_ptr run)
{
m_source_trans target;
transition tmp;

View file

@ -205,11 +205,7 @@ namespace spot
{
// Check the product between LOOP_A, and ORIG_A starting
// in S.
auto ec = couvreur99(product_at(loop_a, ref_, loop_a_init, s));
emptiness_check_result* res = ec->check();
delete res;
delete ec;
if (res)
if (!product_at(loop_a, ref_, loop_a_init, s)->is_empty())
{
accepting = true;
break;
@ -326,9 +322,9 @@ namespace spot
auto det = tba_determinize(aut, threshold_states, threshold_cycles);
if (!det)
return 0;
return nullptr;
if (neg_aut == 0)
if (neg_aut == nullptr)
{
const ltl::formula* neg_f =
ltl::unop::instance(ltl::unop::Not, f->clone());
@ -339,30 +335,13 @@ namespace spot
neg_aut = scc_filter(neg_aut, true);
}
bool ok = false;
auto ec = couvreur99(product(det, neg_aut));
auto res = ec->check();
if (!res)
{
delete ec;
if (product(det, neg_aut)->is_empty())
// Complement the DBA.
ec = couvreur99(product(aut, dtgba_complement(det)));
res = ec->check();
if (!res)
{
if (product(aut, dtgba_complement(det))->is_empty())
// Finally, we are now sure that it was safe
// to determinize the automaton.
ok = true;
}
}
delete res;
delete ec;
if (ok)
return det;
return aut;
}
}

View file

@ -24,12 +24,12 @@
namespace spot
{
tgba_run*
tgba_run_ptr
project_tgba_run(const const_tgba_ptr& a_run,
const const_tgba_ptr& a_proj,
const tgba_run* run)
const const_tgba_run_ptr& run)
{
tgba_run* res = new tgba_run;
auto res = std::make_shared<tgba_run>();
for (tgba_run::steps::const_iterator i = run->prefix.begin();
i != run->prefix.end(); ++i)
{

View file

@ -26,6 +26,7 @@
# include "misc/common.hh"
# include <iosfwd>
# include "tgba/fwd.hh"
# include "tgbaalgos/emptiness.hh"
namespace spot
{
@ -41,10 +42,10 @@ namespace spot
/// \param a_run the automata on which the run was generated
/// \param a_proj the automata on which to project the run
/// \return true iff the run could be completed
SPOT_API tgba_run*
SPOT_API tgba_run_ptr
project_tgba_run(const const_tgba_ptr& a_run,
const const_tgba_ptr& a_proj,
const tgba_run* run);
const const_tgba_run_ptr& run);
}
#endif // SPOT_TGBAALGOS_PROJRUN_HH

View file

@ -1,7 +1,8 @@
// Copyright (C) 2011, 2013 Laboratoire de Recherche et Développement
// de l'Epita (LRDE).
// -*- coding: utf-8 -*-
// Copyright (C) 2011, 2013, 2014 Laboratoire de Recherche et
// Développement de l'Epita (LRDE).
// Copyright (C) 2004 Laboratoire d'Informatique de Paris 6 (LIP6),
// département Systèmes Répartis Coopératifs (SRC), Université Pierre
// département Systèmes Répartis Coopératifs (SRC), Université Pierre
// et Marie Curie.
//
// This file is part of Spot, a model checking library.
@ -86,10 +87,10 @@ namespace spot
};
}
tgba_run*
reduce_run(const const_tgba_ptr& a, const tgba_run* org)
tgba_run_ptr
reduce_run(const const_tgba_ptr& a, const const_tgba_run_ptr& org)
{
tgba_run* res = new tgba_run;
auto res = std::make_shared<tgba_run>();
state_set ss;
shortest_path shpath(a);
shpath.set_target(&ss);

View file

@ -25,18 +25,17 @@
# include "misc/common.hh"
# include "tgba/fwd.hh"
# include "tgbaalgos/emptiness.hh"
namespace spot
{
struct tgba_run;
/// \ingroup tgba_run
/// \brief Reduce an accepting run.
///
/// Return a run which is accepting for \a a and that is no longer
/// than \a org.
SPOT_API tgba_run*
reduce_run(const const_tgba_ptr& a, const tgba_run* org);
SPOT_API tgba_run_ptr
reduce_run(const const_tgba_ptr& a, const const_tgba_run_ptr& org);
}
#endif // SPOT_TGBAALGOS_REDUCERUN_HH

View file

@ -32,7 +32,8 @@ namespace spot
namespace
{
void
print_annotation(std::ostream& os, const_tgba_ptr a,
print_annotation(std::ostream& os,
const const_tgba_ptr& a,
const tgba_succ_iterator* i)
{
std::string s = a->transition_annotation(i);
@ -44,7 +45,7 @@ namespace spot
bool
replay_tgba_run(std::ostream& os, const const_tgba_ptr& a,
const tgba_run* run, bool debug)
const const_tgba_run_ptr& run, bool debug)
{
const state* s = a->get_init_state();
int serial = 1;

View file

@ -26,6 +26,7 @@
# include "misc/common.hh"
# include <iosfwd>
# include "tgba/fwd.hh"
# include "tgbaalgos/emptiness.hh"
namespace spot
{
@ -48,7 +49,8 @@ namespace spot
/// \return true iff the run could be completed
SPOT_API bool
replay_tgba_run(std::ostream& os,
const const_tgba_ptr& a, const tgba_run* run,
const const_tgba_ptr& a,
const const_tgba_run_ptr& run,
bool debug = false);
}

View file

@ -26,7 +26,8 @@
namespace spot
{
tgba_run_dotty_decorator::tgba_run_dotty_decorator(const tgba_run* run)
tgba_run_dotty_decorator::tgba_run_dotty_decorator(const
const_tgba_run_ptr& run)
: run_(run)
{
int n = 1;

View file

@ -38,7 +38,7 @@ namespace spot
class SPOT_API tgba_run_dotty_decorator: public dotty_decorator
{
public:
tgba_run_dotty_decorator(const tgba_run* run);
tgba_run_dotty_decorator(const const_tgba_run_ptr& run);
virtual ~tgba_run_dotty_decorator();
virtual std::string state_decl(const const_tgba_ptr& a,
@ -52,7 +52,7 @@ namespace spot
const tgba_succ_iterator* si,
const std::string& label);
private:
const tgba_run* run_;
const_tgba_run_ptr run_;
typedef std::pair<tgba_run::steps::const_iterator, int> step_num;
typedef std::list<step_num> step_set;
typedef std::map<const state*, std::pair<step_set, step_set>,

View file

@ -88,8 +88,10 @@ namespace spot
/// check() can be called several times (until it returns a null
/// pointer) to enumerate all the visited accepting paths. The method
/// visits only a finite set of accepting paths.
virtual emptiness_check_result* check()
virtual emptiness_check_result_ptr check()
{
auto t = std::static_pointer_cast<se05_search>
(this->emptiness_check::shared_from_this());
if (st_red.empty())
{
assert(st_blue.empty());
@ -98,17 +100,17 @@ namespace spot
h.add_new_state(s0, CYAN);
push(st_blue, s0, bddfalse, bddfalse);
if (dfs_blue())
return new se05_result(*this, options());
return std::make_shared<se05_result>(t, options());
}
else
{
h.pop_notify(st_red.front().s);
pop(st_red);
if (!st_red.empty() && dfs_red())
return new se05_result(*this, options());
return std::make_shared<se05_result>(t, options());
else
if (dfs_blue())
return new se05_result(*this, options());
return std::make_shared<se05_result>(t, options());
}
return 0;
}
@ -330,27 +332,27 @@ namespace spot
public acss_statistics
{
public:
result_from_stack(se05_search& ms)
: emptiness_check_result(ms.automaton()), ms_(ms)
result_from_stack(const std::shared_ptr<se05_search>& ms)
: emptiness_check_result(ms->automaton()), ms_(ms)
{
}
virtual tgba_run* accepting_run()
virtual tgba_run_ptr accepting_run()
{
assert(!ms_.st_blue.empty());
assert(!ms_.st_red.empty());
assert(!ms_->st_blue.empty());
assert(!ms_->st_red.empty());
tgba_run* run = new tgba_run;
auto run = std::make_shared<tgba_run>();
typename stack_type::const_reverse_iterator i, j, end;
tgba_run::steps* l;
const state* target = ms_.st_red.front().s;
const state* target = ms_->st_red.front().s;
l = &run->prefix;
i = ms_.st_blue.rbegin();
end = ms_.st_blue.rend(); --end;
i = ms_->st_blue.rbegin();
end = ms_->st_blue.rend(); --end;
j = i; ++j;
for (; i != end; ++i, ++j)
{
@ -364,12 +366,12 @@ namespace spot
l = &run->cycle;
assert(l == &run->cycle);
j = ms_.st_red.rbegin();
j = ms_->st_red.rbegin();
tgba_run::step s = { i->s->clone(), j->label, j->acc };
l->push_back(s);
i = j; ++j;
end = ms_.st_red.rend(); --end;
end = ms_->st_red.rend(); --end;
for (; i != end; ++i, ++j)
{
tgba_run::step s = { i->s->clone(), j->label, j->acc };
@ -384,7 +386,7 @@ namespace spot
return 0;
}
private:
se05_search& ms_;
std::shared_ptr<se05_search> ms_;
};
# define FROM_STACK "ar:from_stack"
@ -392,8 +394,9 @@ namespace spot
class se05_result: public emptiness_check_result
{
public:
se05_result(se05_search& m, option_map o = option_map())
: emptiness_check_result(m.automaton(), o), ms(m)
se05_result(const std::shared_ptr<se05_search>& m,
option_map o = option_map())
: emptiness_check_result(m->automaton(), o), ms(m)
{
if (options()[FROM_STACK])
computer = new result_from_stack(ms);
@ -420,7 +423,7 @@ namespace spot
delete computer;
}
virtual tgba_run* accepting_run()
virtual tgba_run_ptr accepting_run()
{
return computer->accepting_run();
}
@ -432,7 +435,7 @@ namespace spot
private:
emptiness_check_result* computer;
se05_search& ms;
std::shared_ptr<se05_search> ms;
};
};
@ -675,19 +678,20 @@ namespace spot
} // anonymous
emptiness_check* explicit_se05_search(const const_tgba_ptr& a, option_map o)
emptiness_check_ptr
explicit_se05_search(const const_tgba_ptr& a, option_map o)
{
return new se05_search<explicit_se05_search_heap>(a, 0, o);
return std::make_shared<se05_search<explicit_se05_search_heap>>(a, 0, o);
}
emptiness_check* bit_state_hashing_se05_search(const const_tgba_ptr& a,
size_t size,
option_map o)
emptiness_check_ptr
bit_state_hashing_se05_search(const const_tgba_ptr& a,
size_t size, option_map o)
{
return new se05_search<bsh_se05_search_heap>(a, size, o);
return std::make_shared<se05_search<bsh_se05_search_heap>>(a, size, o);
}
emptiness_check*
emptiness_check_ptr
se05(const const_tgba_ptr& a, option_map o)
{
size_t size = o.get("bsh");

View file

@ -26,11 +26,10 @@
# include <cstddef>
# include "misc/optionmap.hh"
# include "tgba/fwd.hh"
# include "emptiness.hh"
namespace spot
{
class emptiness_check;
/// \addtogroup emptiness_check_algorithms
/// @{
@ -102,7 +101,7 @@ namespace spot
///
/// \sa spot::explicit_magic_search
///
SPOT_API emptiness_check*
SPOT_API emptiness_check_ptr
explicit_se05_search(const const_tgba_ptr& a, option_map o = option_map());
/// \brief Returns an emptiness checker on the spot::tgba automaton \a a.
@ -132,7 +131,7 @@ namespace spot
///
/// \sa spot::explicit_se05_search
///
SPOT_API emptiness_check*
SPOT_API emptiness_check_ptr
bit_state_hashing_se05_search(const const_tgba_ptr& a, size_t size,
option_map o = option_map());
@ -143,7 +142,7 @@ namespace spot
/// bit_state_hashing_se05_search() according to the \c "bsh" option
/// in the \c option_map. If \c "bsh" is set and non null, its value
/// is used as the size of the hash map.
SPOT_API emptiness_check*
SPOT_API emptiness_check_ptr
se05(const const_tgba_ptr& a, option_map o);
/// @}

View file

@ -83,18 +83,20 @@ namespace spot
///
/// \return non null pointer iff the algorithm has found an
/// accepting path.
virtual emptiness_check_result* check()
virtual emptiness_check_result_ptr check()
{
if (!st_blue.empty())
return 0;
return nullptr;
assert(st_red.empty());
const state* s0 = a_->get_init_state();
inc_states();
h.add_new_state(s0, BLUE);
push(st_blue, s0, bddfalse, bddfalse);
auto t = std::static_pointer_cast<tau03_search>
(this->emptiness_check::shared_from_this());
if (dfs_blue())
return new ndfs_result<tau03_search<heap>, heap>(*this);
return 0;
return std::make_shared<ndfs_result<tau03_search<heap>, heap>>(t);
return nullptr;
}
virtual std::ostream& print_stats(std::ostream &os) const
@ -374,9 +376,10 @@ namespace spot
} // anonymous
emptiness_check* explicit_tau03_search(const const_tgba_ptr& a, option_map o)
emptiness_check_ptr
explicit_tau03_search(const const_tgba_ptr& a, option_map o)
{
return new tau03_search<explicit_tau03_search_heap>(a, 0, o);
return std::make_shared<tau03_search<explicit_tau03_search_heap>>(a, 0, o);
}
}

View file

@ -25,11 +25,10 @@
# include "misc/optionmap.hh"
# include "tgba/fwd.hh"
# include "emptiness.hh"
namespace spot
{
class emptiness_check;
/// \addtogroup emptiness_check_algorithms
/// @{
@ -96,7 +95,7 @@ namespace spot
}
\endverbatim */
///
SPOT_API emptiness_check*
SPOT_API emptiness_check_ptr
explicit_tau03_search(const const_tgba_ptr& a, option_map o = option_map());
/// @}

View file

@ -108,18 +108,20 @@ namespace spot
///
/// \return non null pointer iff the algorithm has found an
/// accepting path.
virtual emptiness_check_result* check()
virtual emptiness_check_result_ptr check()
{
if (!st_blue.empty())
return 0;
return nullptr;
assert(st_red.empty());
const state* s0 = a_->get_init_state();
inc_states();
h.add_new_state(s0, CYAN, current_weight);
push(st_blue, s0, bddfalse, bddfalse);
auto t = std::static_pointer_cast<tau03_opt_search>
(this->emptiness_check::shared_from_this());
if (dfs_blue())
return new ndfs_result<tau03_opt_search<heap>, heap>(*this);
return 0;
return std::make_shared<ndfs_result<tau03_opt_search<heap>, heap>>(t);
return nullptr;
}
virtual std::ostream& print_stats(std::ostream &os) const
@ -572,10 +574,12 @@ namespace spot
} // anonymous
emptiness_check* explicit_tau03_opt_search(const const_tgba_ptr& a,
option_map o)
emptiness_check_ptr
explicit_tau03_opt_search(const const_tgba_ptr& a, option_map o)
{
return new tau03_opt_search<explicit_tau03_opt_search_heap>(a, 0, o);
return
std::make_shared<tau03_opt_search<explicit_tau03_opt_search_heap>>(a,
0, o);
}
}

View file

@ -25,11 +25,10 @@
# include "misc/optionmap.hh"
# include "tgba/fwd.hh"
# include "emptiness.hh"
namespace spot
{
class emptiness_check;
/// \addtogroup emptiness_check_algorithms
/// @{
@ -98,7 +97,7 @@ namespace spot
/// the path stored in the blue stack. Such a vector is associated to each
/// state of this stack.
///
SPOT_API emptiness_check*
SPOT_API emptiness_check_ptr
explicit_tau03_opt_search(const const_tgba_ptr& a,
option_map o = option_map());

View file

@ -23,7 +23,7 @@
namespace spot
{
tgba_word::tgba_word(const tgba_run* run)
tgba_word::tgba_word(const tgba_run_ptr run)
{
for (tgba_run::steps::const_iterator i = run->prefix.begin();
i != run->prefix.end(); ++i)

View file

@ -1,5 +1,5 @@
// -*- coding: utf-8 -*-
// Copyright (C) 2013 Laboratoire de Recherche et Développement de
// Copyright (C) 2013, 2014 Laboratoire de Recherche et Développement de
// l'Epita (LRDE).
//
// This file is part of Spot, a model checking library.
@ -29,7 +29,7 @@ namespace spot
/// \brief An infinite word stored as a lasso.
struct SPOT_API tgba_word
{
tgba_word(const tgba_run* run);
tgba_word(const tgba_run_ptr run);
void simplify();
std::ostream& print(std::ostream& os, const bdd_dict_ptr& d) const;

View file

@ -29,7 +29,6 @@
#include "tgbaalgos/ltl2taa.hh"
#include "tgbaalgos/sccfilter.hh"
#include "tgba/tgbaproduct.hh"
#include "tgbaalgos/gtec/gtec.hh"
#include "tgbaalgos/dotty.hh"
#include "tgbaalgos/dupexp.hh"
@ -76,14 +75,11 @@ main(int argc, char** argv)
{
auto apos = scc_filter(ltl_to_tgba_fm(fpos, d));
auto aneg = scc_filter(ltl_to_tgba_fm(fneg, d));
auto ec = spot::couvreur99(spot::product(apos, aneg));
auto res = ec->check();
if (res)
if (!spot::product(apos, aneg)->is_empty())
{
std::cerr << "non-empty intersection between pos and neg (FM)\n";
exit(2);
}
delete ec;
// Run make_future_conditions_collector, without testing the output.
auto fc = spot::make_future_conditions_collector(apos, true);
@ -93,28 +89,22 @@ main(int argc, char** argv)
{
auto apos = scc_filter(ltl_to_tgba_fm(fpos, d, true));
auto aneg = scc_filter(ltl_to_tgba_fm(fneg, d, true));
auto ec = spot::couvreur99(spot::product(apos, aneg));
auto res = ec->check();
if (res)
if (!spot::product(apos, aneg)->is_empty())
{
std::cerr << "non-empty intersection between pos and neg (FM -x)\n";
exit(2);
}
delete ec;
}
if (fpos->is_ltl_formula())
{
auto apos = scc_filter(spot::tgba_dupexp_dfs(ltl_to_taa(fpos, d)));
auto aneg = scc_filter(spot::tgba_dupexp_dfs(ltl_to_taa(fneg, d)));
auto ec = spot::couvreur99(spot::product(apos, aneg));
auto res = ec->check();
if (res)
if (!spot::product(apos, aneg)->is_empty())
{
std::cerr << "non-empty intersection between pos and neg (TAA)\n";
exit(2);
}
delete ec;
}
fpos->destroy();
fneg->destroy();

View file

@ -274,8 +274,8 @@ int main(int argc, char* argv[])
nAf = spot::make_kv_complement(Af);
nAnf = spot::make_kv_complement(Anf);
}
spot::emptiness_check* ec = spot::couvreur99(spot::product(nAf, nAnf));
spot::emptiness_check_result* res = ec->check();
auto ec = spot::couvreur99(spot::product(nAf, nAnf));
auto res = ec->check();
spot::tgba_statistics a_size = spot::stats_reachable(ec->automaton());
std::cout << "States: "
<< a_size.states << std::endl
@ -292,12 +292,8 @@ int main(int argc, char* argv[])
else
std::cout << "OK";
std::cout << std::endl;
delete res;
delete ec;
nf1->destroy();
f1->destroy();
}
return return_value;

View file

@ -122,7 +122,7 @@ main(int argc, char** argv)
for (auto& algo: algos)
{
const char* err;
auto i = spot::emptiness_check_instantiator::construct(algo, &err);
auto i = spot::make_emptiness_check_instantiator(algo, &err);
if (!i)
{
std::cerr << "Failed to parse `" << err << '\'' << std::endl;
@ -157,17 +157,14 @@ main(int argc, char** argv)
int ce_found = 0;
do
{
auto res = ec->check();
if (res)
if (auto res = ec->check())
{
++ce_found;
std::cout << ce_found << " counterexample found\n";
auto run = res->accepting_run();
if (run)
if (auto run = res->accepting_run())
{
auto ar = spot::tgba_run_to_tgba(a, run);
spot::dotty_reachable(std::cout, ar, false);
delete run;
}
std::cout << '\n';
if (runs == 0)
@ -175,7 +172,6 @@ main(int argc, char** argv)
std::cerr << "ERROR: Expected no counterexample.\n";
exit(1);
}
delete res;
}
else
{
@ -201,10 +197,7 @@ main(int argc, char** argv)
std::cerr << "ERROR: expected a counterexample.\n";
exit(1);
}
delete ec;
}
delete i;
}
f->destroy();
}

View file

@ -354,7 +354,7 @@ checked_main(int argc, char** argv)
int output = 0;
int formula_index = 0;
const char* echeck_algo = 0;
spot::emptiness_check_instantiator* echeck_inst = 0;
spot::emptiness_check_instantiator_ptr echeck_inst = 0;
enum { NoneDup, BFS, DFS } dupexp = NoneDup;
bool expect_counter_example = false;
bool accepting_run = false;
@ -500,7 +500,7 @@ checked_main(int argc, char** argv)
const char* err;
echeck_inst =
spot::emptiness_check_instantiator::construct(echeck_algo, &err);
spot::make_emptiness_check_instantiator(echeck_algo, &err);
if (!echeck_inst)
{
std::cerr << "Failed to parse argument of -e near `"
@ -518,7 +518,7 @@ checked_main(int argc, char** argv)
const char* err;
echeck_inst =
spot::emptiness_check_instantiator::construct(echeck_algo, &err);
spot::make_emptiness_check_instantiator(echeck_algo, &err);
if (!echeck_inst)
{
std::cerr << "Failed to parse argument of -e near `"
@ -1713,13 +1713,13 @@ checked_main(int argc, char** argv)
if (echeck_inst)
{
spot::emptiness_check* ec = echeck_inst->instantiate(a);
auto ec = echeck_inst->instantiate(a);
bool search_many = echeck_inst->options().get("repeated");
assert(ec);
do
{
tm.start("running emptiness check");
spot::emptiness_check_result* res = ec->check();
auto res = ec->check();
tm.stop("running emptiness check");
if (paper_opt)
@ -1736,8 +1736,7 @@ checked_main(int argc, char** argv)
std::cout <<
ec->automaton()->number_of_acceptance_conditions()
<< ", ";
const spot::ec_statistics* ecs =
dynamic_cast<const spot::ec_statistics*>(ec);
auto ecs = ec->emptiness_check_statistics();
if (ecs)
std::cout << std::right << std::setw(10)
<< ecs->states() << ", "
@ -1781,7 +1780,7 @@ checked_main(int argc, char** argv)
{
tm.start("computing accepting run");
spot::tgba_run* run = res->accepting_run();
auto run = res->accepting_run();
tm.stop("computing accepting run");
if (!run)
@ -1793,11 +1792,8 @@ checked_main(int argc, char** argv)
if (opt_reduce)
{
tm.start("reducing accepting run");
spot::tgba_run* redrun =
spot::reduce_run(res->automaton(), run);
run = spot::reduce_run(res->automaton(), run);
tm.stop("reducing accepting run");
delete run;
run = redrun;
}
if (accepting_run_replay)
{
@ -1827,7 +1823,6 @@ checked_main(int argc, char** argv)
}
tm.stop("printing accepting run");
}
delete run;
}
}
else
@ -1836,14 +1831,11 @@ checked_main(int argc, char** argv)
<< "(use -C to print it)" << std::endl;
}
}
delete res;
}
while (search_many);
delete ec;
}
if (f)
f->destroy();
delete echeck_inst;
}
else
{

View file

@ -59,7 +59,7 @@
struct ec_algo
{
std::string name;
spot::emptiness_check_instantiator* inst;
spot::emptiness_check_instantiator_ptr inst;
};
const char* default_algos[] = {
@ -84,12 +84,12 @@ const char* default_algos[] = {
std::vector<ec_algo> ec_algos;
spot::emptiness_check*
spot::emptiness_check_ptr
cons_emptiness_check(int num, spot::const_tgba_ptr a,
const spot::const_tgba_ptr& degen,
unsigned int n_acc)
{
spot::emptiness_check_instantiator* inst = ec_algos[num].inst;
auto inst = ec_algos[num].inst;
if (n_acc < inst->min_acceptance_conditions()
|| n_acc > inst->max_acceptance_conditions())
a = degen;
@ -380,7 +380,7 @@ struct ar_stat
}
void
count(const spot::tgba_run* run)
count(const spot::const_tgba_run_ptr& run)
{
int p = run->prefix.size();
int c = run->cycle.size();
@ -837,8 +837,7 @@ main(int argc, char** argv)
{
const char* err;
ec_algos[i].inst =
spot::emptiness_check_instantiator::construct(ec_algos[i]
.name.c_str(),
spot::make_emptiness_check_instantiator(ec_algos[i].name.c_str(),
&err);
if (ec_algos[i].inst == 0)
{
@ -939,9 +938,7 @@ main(int argc, char** argv)
for (int i = 0; i < n_alg; ++i)
{
spot::emptiness_check* ec;
spot::emptiness_check_result* res;
ec = cons_emptiness_check(i, a, degen, real_n_acc);
auto ec = cons_emptiness_check(i, a, degen, real_n_acc);
if (!ec)
continue;
++n_ec;
@ -952,17 +949,16 @@ main(int argc, char** argv)
std::cout << algo << ": ";
}
tm_ec.start(algo);
spot::emptiness_check_result_ptr res;
for (int count = opt_R;;)
{
res = ec->check();
if (count-- <= 0)
break;
delete res;
delete ec;
ec = cons_emptiness_check(i, a, degen, real_n_acc);
}
tm_ec.stop(algo);
const spot::unsigned_statistics* ecs = ec->statistics();
auto ecs = ec->statistics();
if (opt_z && res)
{
// Notice that ratios are computed w.r.t. the
@ -1001,7 +997,7 @@ main(int argc, char** argv)
++n_non_empty;
if (opt_replay)
{
spot::tgba_run* run;
spot::tgba_run_ptr run;
bool done = false;
tm_ar.start(algo);
for (int count = opt_R;;)
@ -1030,7 +1026,6 @@ main(int argc, char** argv)
if (count-- <= 0 || !run)
break;
delete run;
}
if (!run)
{
@ -1065,7 +1060,7 @@ main(int argc, char** argv)
if (opt_reduce)
{
spot::tgba_run* redrun =
auto redrun =
spot::reduce_run(res->automaton(), run);
if (!spot::replay_tgba_run(s,
res
@ -1093,14 +1088,11 @@ main(int argc, char** argv)
<< redrun->cycle.size()
<< ']';
}
delete redrun;
}
delete run;
}
}
if (!opt_paper)
std::cout << std::endl;
delete res;
}
else
{
@ -1122,7 +1114,6 @@ main(int argc, char** argv)
if (opt_Z && !opt_paper)
ec->print_stats(std::cout);
delete ec;
}
assert(n_empty + n_non_empty + n_maybe_empty == n_ec);
@ -1310,10 +1301,6 @@ main(int argc, char** argv)
delete formula_file;
}
if (opt_ec)
for (unsigned i = 0; i < ec_algos.size(); ++i)
delete ec_algos[i].inst;
delete ap;
delete apf;
return exit_code;

View file

@ -102,7 +102,6 @@ if not script:
httpd.serve_forever()
import cgi
import cgitb; cgitb.enable()
import signal
import time
import os.path
@ -120,6 +119,9 @@ sys.stdout = os.fdopen(sys.stdout.fileno(), "wb", 0)
# even errors from subprocesses get printed).
os.dup2(sys.stdout.fileno(), sys.stderr.fileno())
import cgitb
sys.excepthook = cgitb.Hook(file=sys.stderr)
# Create the temporary cache directory
os.mkdir(tmpdir, 493) # See comment above about 0o755 or 0755.
@ -533,7 +535,7 @@ elif translator == 'ta':
refined_rules = False
if form.getfirst('ta', '') == 'lc':
refined_rules = True
automaton = spot.ltl_to_taa(f, dict, refined_rules)
automaton = spot.tgba_dupexp_dfs(spot.ltl_to_taa(f, dict, refined_rules))
elif translator == 'l3':
l3out = '-T'
l3opt = { '-l', '-P', '-A', '-c', '-C', '-o', '-p' }
@ -770,7 +772,7 @@ if output_type == 'r':
err = ""
opt = (form.getfirst('ec', 'Cou99') + "(" +
form.getfirst('eo', '') + ")")
eci, err = spot.emptiness_check_instantiator.construct(opt)
eci, err = spot.make_emptiness_check_instantiator(opt)
if not eci:
unbufprint('<div class="parse-error">Cannot parse "' + opt
@ -824,8 +826,4 @@ if output_type == 'r':
del ec_run
del ec_res
unbufprint('</div>')
del ec
del ec_a
degen = 0
automaton = 0
finish()

View file

@ -36,7 +36,6 @@
// sed 's/.*<\(.*\)>.*/%shared_ptr(spot::\1)/g'
%shared_ptr(spot::bdd_dict)
%shared_ptr(spot::dstar_aut)
%shared_ptr(spot::dstar_aut)
%shared_ptr(spot::future_conditions_collector)
%shared_ptr(spot::kripke)
%shared_ptr(spot::saba)
@ -56,6 +55,10 @@
%shared_ptr(spot::tgba_sgba_proxy)
%shared_ptr(spot::tgta)
%shared_ptr(spot::tgta_explicit)
%shared_ptr(spot::tgba_run)
%shared_ptr(spot::emptiness_check)
%shared_ptr(spot::emptiness_check_result)
%shared_ptr(spot::emptiness_check_instantiator)
namespace std {
%template(liststr) list<string>;
@ -203,19 +206,8 @@ using namespace spot;
%include "ltlvisit/simplify.hh"
%include "ltlvisit/tostring.hh"
%include "ltlvisit/tunabbrev.hh"
%include "ltlvisit/apcollect.hh"
%include "ltlvisit/lbt.hh"
%feature("new") spot::emptiness_check::check;
%feature("new") spot::emptiness_check_instantiator::construct;
%feature("new") spot::emptiness_check_instantiator::instanciate;
%feature("new") spot::emptiness_check_result::accepting_run;
%feature("new") spot::explicit_magic_search;
%feature("new") spot::explicit_se05_search;
%feature("new") spot::tgba::get_init_state;
%feature("new") spot::tgba::succ_iter;
%feature("new") spot::tgba_succ_iterator::current_state;
// Help SWIG with namespace lookups.
#define ltl spot::ltl
%include "tgba/bddprint.hh"
@ -232,6 +224,9 @@ namespace spot {
};
}
// Should come after the definition of tgba_digraph
%include "ltlvisit/apcollect.hh"
%include "tgbaalgos/degen.hh"
%include "tgbaalgos/dottydec.hh"
%include "tgbaalgos/dotty.hh"