Commit 8c0d1003 authored by Damien Lefortier's avatar Damien Lefortier
Browse files

Start the ELTL translation (LACIM).

Merge all eltlast/ files into formula.hh (except automatop.hh).
parent 86230259
2008-06-12 Damien Lefortier <dam@lrde.epita.fr>
Add ELTL visitors in eltlvisit/ and start the ELTL translation (LACIM).
Merge all eltlast/ files into formula.hh (except automatop.hh).
* src/eltlast/allnodes.hh, src/eltlast/atomic_prop.hh,
src/eltlast/binop.hh, src/eltlast/constant.hh, src/eltlast/multop.hh,
src/eltlast/refformula.hh, src/eltlast/unop.hh,
src/eltlast/visitor.hh: Delete and merge all these files into ...
* src/eltlast/formula.hh: ... this one.
* src/eltlvisit/: Add some visitors (clone, destroy, ...).
* src/internal/baseformula.hh, src/internal/baseformula.cc:
Add base_formula, a new base class of internal::formula.
* src/tgba/bdddict.cc src/tgba/bdddict.hh, src/tgba/bddprint.cc,
src/tgba/tgbabddconcretefactory.cc, src/tgba/tgbabddconcretefactory.hh
Replace ltl::formula by internal::base_formula.
* src/tgbatest/eltl2tgba.cc: Beginning of the ELTL translation (LACIM).
* m4/boost.m4: Add AX_BOOST_BASE([MINIMUM-VERSION]).
2008-06-12 Alexandre Duret-Lutz <adl@lrde.epita.fr>
* iface/nips/nipstest/dotty.test,
......
......@@ -44,6 +44,7 @@ AC_LANG(C++)
AX_CHECK_BUDDY
AX_CHECK_LBTT
AX_CHECK_GSPNLIB
AX_BOOST_BASE([1.34])
AC_CHECK_FUNCS([srand48 drand48])
......@@ -88,6 +89,7 @@ AC_CONFIG_FILES([
src/eltlparse/Makefile
src/eltltest/Makefile
src/eltltest/defs
src/eltlvisit/Makefile
src/evtgba/Makefile
src/evtgbaalgos/Makefile
src/evtgbaparse/Makefile
......
##### http://autoconf-archive.cryp.to/ax_boost_base.html
#
# SYNOPSIS
#
# AX_BOOST_BASE([MINIMUM-VERSION])
#
# DESCRIPTION
#
# Test for the Boost C++ libraries of a particular version (or newer)
#
# If no path to the installed boost library is given the macro
# searchs under /usr, /usr/local, /opt and /opt/local and evaluates
# the $BOOST_ROOT environment variable. Further documentation is
# available at <http://randspringer.de/boost/index.html>.
#
# This macro calls:
#
# AC_SUBST(BOOST_CPPFLAGS) / AC_SUBST(BOOST_LDFLAGS)
#
# And sets:
#
# HAVE_BOOST
#
# LAST MODIFICATION
#
# 2007-07-28
#
# COPYLEFT
#
# Copyright (c) 2007 Thomas Porschberg <thomas@randspringer.de>
#
# Copying and distribution of this file, with or without
# modification, are permitted in any medium without royalty provided
# the copyright notice and this notice are preserved.
AC_DEFUN([AX_BOOST_BASE],
[
AC_ARG_WITH([boost],
AS_HELP_STRING([--with-boost@<:@=DIR@:>@], [use boost (default is yes) - it is possible to specify the root directory for boost (optional)]),
[
if test "$withval" = "no"; then
want_boost="no"
elif test "$withval" = "yes"; then
want_boost="yes"
ac_boost_path=""
else
want_boost="yes"
ac_boost_path="$withval"
fi
],
[want_boost="yes"])
if test "x$want_boost" = "xyes"; then
boost_lib_version_req=ifelse([$1], ,1.20.0,$1)
boost_lib_version_req_shorten=`expr $boost_lib_version_req : '\([[0-9]]*\.[[0-9]]*\)'`
boost_lib_version_req_major=`expr $boost_lib_version_req : '\([[0-9]]*\)'`
boost_lib_version_req_minor=`expr $boost_lib_version_req : '[[0-9]]*\.\([[0-9]]*\)'`
boost_lib_version_req_sub_minor=`expr $boost_lib_version_req : '[[0-9]]*\.[[0-9]]*\.\([[0-9]]*\)'`
if test "x$boost_lib_version_req_sub_minor" = "x" ; then
boost_lib_version_req_sub_minor="0"
fi
WANT_BOOST_VERSION=`expr $boost_lib_version_req_major \* 100000 \+ $boost_lib_version_req_minor \* 100 \+ $boost_lib_version_req_sub_minor`
AC_MSG_CHECKING(for boostlib >= $boost_lib_version_req)
succeeded=no
dnl first we check the system location for boost libraries
dnl this location ist chosen if boost libraries are installed with the --layout=system option
dnl or if you install boost with RPM
if test "$ac_boost_path" != ""; then
BOOST_LDFLAGS="-L$ac_boost_path/lib"
BOOST_CPPFLAGS="-I$ac_boost_path/include"
else
for ac_boost_path_tmp in /usr /usr/local /opt /opt/local ; do
if test -d "$ac_boost_path_tmp/include/boost" && test -r "$ac_boost_path_tmp/include/boost"; then
BOOST_LDFLAGS="-L$ac_boost_path_tmp/lib"
BOOST_CPPFLAGS="-I$ac_boost_path_tmp/include"
break;
fi
done
fi
CPPFLAGS_SAVED="$CPPFLAGS"
CPPFLAGS="$CPPFLAGS $BOOST_CPPFLAGS"
LDFLAGS_SAVED="$LDFLAGS"
LDFLAGS="$LDFLAGS $BOOST_LDFLAGS"
AC_LANG_PUSH(C++)
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[
@%:@include <boost/version.hpp>
]], [[
#if BOOST_VERSION >= $WANT_BOOST_VERSION
// Everything is okay
#else
# error Boost version is too old
#endif
]])],[
AC_MSG_RESULT(yes)
succeeded=yes
found_system=yes
],[
])
AC_LANG_POP([C++])
dnl if we found no boost with system layout we search for boost libraries
dnl built and installed without the --layout=system option or for a staged(not installed) version
if test "x$succeeded" != "xyes"; then
_version=0
if test "$ac_boost_path" != ""; then
BOOST_LDFLAGS="-L$ac_boost_path/lib"
if test -d "$ac_boost_path" && test -r "$ac_boost_path"; then
for i in `ls -d $ac_boost_path/include/boost-* 2>/dev/null`; do
_version_tmp=`echo $i | sed "s#$ac_boost_path##" | sed 's/\/include\/boost-//' | sed 's/_/./'`
V_CHECK=`expr $_version_tmp \> $_version`
if test "$V_CHECK" = "1" ; then
_version=$_version_tmp
fi
VERSION_UNDERSCORE=`echo $_version | sed 's/\./_/'`
BOOST_CPPFLAGS="-I$ac_boost_path/include/boost-$VERSION_UNDERSCORE"
done
fi
else
for ac_boost_path in /usr /usr/local /opt /opt/local ; do
if test -d "$ac_boost_path" && test -r "$ac_boost_path"; then
for i in `ls -d $ac_boost_path/include/boost-* 2>/dev/null`; do
_version_tmp=`echo $i | sed "s#$ac_boost_path##" | sed 's/\/include\/boost-//' | sed 's/_/./'`
V_CHECK=`expr $_version_tmp \> $_version`
if test "$V_CHECK" = "1" ; then
_version=$_version_tmp
best_path=$ac_boost_path
fi
done
fi
done
VERSION_UNDERSCORE=`echo $_version | sed 's/\./_/'`
BOOST_CPPFLAGS="-I$best_path/include/boost-$VERSION_UNDERSCORE"
BOOST_LDFLAGS="-L$best_path/lib"
if test "x$BOOST_ROOT" != "x"; then
if test -d "$BOOST_ROOT" && test -r "$BOOST_ROOT" && test -d "$BOOST_ROOT/stage/lib" && test -r "$BOOST_ROOT/stage/lib"; then
version_dir=`expr //$BOOST_ROOT : '.*/\(.*\)'`
stage_version=`echo $version_dir | sed 's/boost_//' | sed 's/_/./g'`
stage_version_shorten=`expr $stage_version : '\([[0-9]]*\.[[0-9]]*\)'`
V_CHECK=`expr $stage_version_shorten \>\= $_version`
if test "$V_CHECK" = "1" ; then
AC_MSG_NOTICE(We will use a staged boost library from $BOOST_ROOT)
BOOST_CPPFLAGS="-I$BOOST_ROOT"
BOOST_LDFLAGS="-L$BOOST_ROOT/stage/lib"
fi
fi
fi
fi
CPPFLAGS="$CPPFLAGS $BOOST_CPPFLAGS"
LDFLAGS="$LDFLAGS $BOOST_LDFLAGS"
AC_LANG_PUSH(C++)
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[
@%:@include <boost/version.hpp>
]], [[
#if BOOST_VERSION >= $WANT_BOOST_VERSION
// Everything is okay
#else
# error Boost version is too old
#endif
]])],[
AC_MSG_RESULT(yes)
succeeded=yes
found_system=yes
],[
])
AC_LANG_POP([C++])
fi
if test "$succeeded" != "yes" ; then
CPPFLAGS="$CPPFLAGS_SAVED"
LDFLAGS="$LDFLAGS_SAVED"
if test "$_version" = "0" ; then
AC_MSG_ERROR([[We could not detect the boost libraries (version $boost_lib_version_req_shorten or higher). If you have a staged boost library (still not installed) please specify \$BOOST_ROOT in your environment and do not give a PATH to --with-boost option. If you are sure you have boost installed, then check your version number looking in <boost/version.hpp>. See http://randspringer.de/boost for more documentation.]])
else
AC_MSG_NOTICE([Your boost libraries seems to old (version $_version).])
fi
else
AC_SUBST(BOOST_CPPFLAGS)
AC_SUBST(BOOST_LDFLAGS)
AC_DEFINE(HAVE_BOOST,,[define if the Boost library is available])
fi
fi
])
......@@ -24,7 +24,7 @@ AUTOMAKE_OPTIONS = subdir-objects
# List directories in the order they must be built.
# Keep tests at the end.
SUBDIRS = misc ltlenv ltlast ltlvisit ltlparse internal \
eltlenv eltlast eltlparse \
eltlenv eltlast eltlvisit eltlparse \
tgba tgbaalgos tgbaparse \
evtgba evtgbaalgos evtgbaparse . \
ltltest eltltest tgbatest evtgbatest sanity
......@@ -36,8 +36,10 @@ libspot_la_LIBADD = \
misc/libmisc.la \
ltlparse/libltlparse.la \
ltlvisit/libltlvisit.la \
internal/libinternal.la \
eltlast/libeltlast.la \
eltlparse/libeltlparse.la \
eltlvisit/libeltlvisit.la \
tgba/libtgba.la \
tgbaalgos/libtgbaalgos.la \
tgbaparse/libtgbaparse.la \
......
......@@ -25,20 +25,11 @@ AM_CXXFLAGS = $(WARNING_CXXFLAGS)
eltlastdir = $(pkgincludedir)/eltlast
eltlast_HEADERS = \
allnodes.hh \
atomic_prop.hh \
automatop.hh \
binop.hh \
constant.hh \
formula.hh \
multop.hh \
nfa.hh \
refformula.hh \
unop.hh \
visitor.hh
nfa.hh
noinst_LTLIBRARIES = libeltlast.la
libeltlast_la_SOURCES = \
automatop.cc \
nfa.cc
\ No newline at end of file
nfa.cc
// Copyright (C) 2003, 2004 Laboratoire d'Informatique de Paris 6 (LIP6),
// dpartement Systmes Rpartis Coopratifs (SRC), Universit Pierre
// et Marie Curie.
//
// This file is part of Spot, a model checking library.
//
// Spot is free software; you can redistribute it and/or modify it
// under the terms of the GNU General Public License as published by
// the Free Software Foundation; either version 2 of the License, or
// (at your option) any later version.
//
// Spot is distributed in the hope that it will be useful, but WITHOUT
// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
// License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Spot; see the file COPYING. If not, write to the Free
// Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
// 02111-1307, USA.
/// \file eltlast/allnodes.hh
/// \brief Define all ELTL node types.
///
/// This file is usually needed when \b defining a visitor.
#ifndef SPOT_ELTLAST_ALLNODES_HH
# define SPOT_ELTLAST_ALLNODES_HH
# include "binop.hh"
# include "unop.hh"
# include "multop.hh"
# include "atomic_prop.hh"
# include "constant.hh"
# include "automatop.hh"
#endif // SPOT_ELTLAST_ALLNODES_HH
......@@ -19,7 +19,6 @@
// Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
// 02111-1307, USA.
#include "visitor.hh"
#include "automatop.hh"
namespace spot
......
......@@ -24,14 +24,16 @@
#ifndef SPOT_ELTLAST_AUTOMATOP_HH
# define SPOT_ELTLAST_AUTOMATOP_HH
# include "multop.hh"
# include "refformula.hh"
# include "formula.hh"
# include "nfa.hh"
namespace spot
{
namespace eltl
{
/// \brief Counted-reference formulae.
/// \ingroup eltl_ast
typedef spot::internal::ref_formula<eltl_t> ref_formula;
/// \brief Automaton operators.
/// \ingroup eltl_ast
......
......@@ -25,6 +25,11 @@
# define SPOT_ELTLAST_FORMULA_HH
# include "internal/formula.hh"
# include "internal/atomic_prop.hh"
# include "internal/constant.hh"
# include "internal/unop.hh"
# include "internal/binop.hh"
# include "internal/multop.hh"
namespace spot
{
......@@ -40,7 +45,21 @@ namespace spot
/// \addtogroup eltl_ast ELTL Abstract Syntax Tree
/// \ingroup eltl
/// \addtogroup eltl_environment ELTL environments
/// \ingroup eltl
/// ELTL environment implementations.
/// \addtogroup eltl_algorithm Algorithms for ELTL formulae
/// \ingroup eltl
/// \addtogroup eltl_io Input/Output of ELTL formulae
/// \ingroup eltl_algorithm
/// \addtogroup eltl_visitor Derivable visitors
/// \ingroup eltl_algorithm
/// Forward declarations
struct eltl_t;
struct visitor;
struct const_visitor;
......@@ -50,11 +69,33 @@ namespace spot
///
/// The only way you can work with a formula is to
/// build a spot::eltl::visitor or spot::eltl::const_visitor.
typedef spot::internal::formula<eltl_t> formula;
/// Forward declarations
formula* clone(const formula* f);
std::ostream& to_string(const formula* f, std::ostream& os);
void destroy(const formula* f);
struct eltl_t
{
typedef spot::eltl::visitor visitor;
typedef spot::eltl::const_visitor const_visitor;
static formula* clone_(const formula* f)
{
return clone(f);
}
static std::ostream& to_string_(const formula* f, std::ostream& os)
{
return to_string(f, os);
}
static void destroy_(const formula* f)
{
destroy(f);
}
enum binop { Xor, Implies, Equiv };
const char* binop_name(binop op) const
{
......@@ -86,10 +127,73 @@ namespace spot
}
};
typedef spot::internal::formula<eltl_t> formula;
typedef spot::internal::formula_ptr_less_than formula_ptr_less_than;
typedef spot::internal::formula_ptr_hash formula_ptr_hash;
/// \brief Atomic propositions.
/// \ingroup eltl_ast
typedef spot::internal::atomic_prop<eltl_t> atomic_prop;
/// \brief A constant (True or False)
/// \ingroup eltl_ast
typedef spot::internal::constant<eltl_t> constant;
/// \brief Unary operators.
/// \ingroup eltl_ast
typedef spot::internal::unop<eltl_t> unop;
/// \brief Binary operator.
/// \ingroup eltl_ast
typedef spot::internal::binop<eltl_t> binop;
/// \brief Multi-operand operators.
/// \ingroup eltl_ast
///
/// These operators are considered commutative and associative.
typedef spot::internal::multop<eltl_t> multop;
// Forward declaration.
struct automatop;
/// \brief Formula visitor that can modify the formula.
/// \ingroup eltl_essential
///
/// Writing visitors is the prefered way
/// to traverse a formula, since it doesn't
/// involve any cast.
///
/// If you do not need to modify the visited formula, inherit from
/// spot::eltl:const_visitor instead.
struct visitor
{
virtual ~visitor() {}
virtual void visit(atomic_prop* node) = 0;
virtual void visit(constant* node) = 0;
virtual void visit(binop* node) = 0;
virtual void visit(unop* node) = 0;
virtual void visit(multop* node) = 0;
virtual void visit(automatop* node) = 0;
};
/// \brief Formula visitor that cannot modify the formula.
///
/// Writing visitors is the prefered way
/// to traverse a formula, since it doesn't
/// involve any cast.
///
/// If you want to modify the visited formula, inherit from
/// spot::eltl:visitor instead.
struct const_visitor
{
virtual ~const_visitor() {}
virtual void visit(const atomic_prop* node) = 0;
virtual void visit(const constant* node) = 0;
virtual void visit(const binop* node) = 0;
virtual void visit(const unop* node) = 0;
virtual void visit(const multop* node) = 0;
virtual void visit(const automatop* node) = 0;
};
typedef spot::internal::formula_ptr_less_than<eltl_t> formula_ptr_less_than;
typedef spot::internal::formula_ptr_hash<eltl_t> formula_ptr_hash;
}
}
......
......@@ -61,7 +61,7 @@ namespace spot
}
void
nfa::add_transition(const std::string& s, const std::string& d, unsigned c)
nfa::add_transition(const std::string& s, const std::string& d, int c)
{
state* source = add_state(s);
nfa::transition* t = new transition;
......@@ -90,7 +90,7 @@ namespace spot
return finals_.find(state) != finals_.end();
}
unsigned
int
nfa::arity()
{
return arity_ + 1;
......
......@@ -51,7 +51,7 @@ namespace spot
/// Explicit transitions.
struct transition
{
unsigned cost;
int cost;
const state* dest;
};
......@@ -59,7 +59,7 @@ namespace spot
~nfa();
void
add_transition(const std::string& s, const std::string& d, unsigned c);
add_transition(const std::string& s, const std::string& d, int c);
void
set_init_state(const std::string& state);
......@@ -72,7 +72,7 @@ namespace spot
is_final(const std::string& state);
/// \brief Get the `arity' i.e. max t.cost, for each transition t.
unsigned
int
arity();
/// \brief Return an iterator on the first succesor (if any) of \a state.
......@@ -103,7 +103,7 @@ namespace spot
sn_map sn_;
state* init_;
unsigned arity_;
int arity_;
std::set<std::string> finals_;
/// Explicitly disllow use of implicity generated member functions
......
......@@ -22,10 +22,11 @@
%{
#include <string>
#include <sstream>
#include <limits>
#include <cerrno>
#include <limits.h>
#include "public.hh"
#include "eltlast/allnodes.hh"
#include "eltlast/automatop.hh"
// Implementation detail for error handling.
namespace spot
......@@ -87,7 +88,8 @@ using namespace spot::eltl;
OP_IMPLIES "implication operator"
OP_EQUIV "equivalent operator"
%token EQ "="
%token ACC "accept"
EQ "="
LPAREN "("
RPAREN ")"
COMMA ","
......@@ -131,6 +133,7 @@ nfa_list: /* empty. */
nfa: IDENT "=" "(" nfa_def ")"
{
nmap[*$1] = nfa::ptr($4);
delete $1;
}
;
......@@ -142,7 +145,8 @@ nfa_def: /* empty. */
{
errno = 0;
long i = strtol($4->c_str(), 0, 10);
if (i > INT_MAX || i < INT_MIN || errno == ERANGE)
if (i > std::numeric_limits<long>::max() ||
i < std::numeric_limits<long>::min() || errno == ERANGE)
{
std::string s = "out of range integer `";
s += *$4;
......@@ -156,7 +160,12 @@ nfa_def: /* empty. */
$1->add_transition(*$2, *$3, i);
$$ = $1;
}
| nfa_def EQ STATE
| nfa_def STATE STATE CONST_TRUE
{
$1->add_transition(*$2, *$3, -1);
$$ = $1;
}
| nfa_def ACC STATE
{
$1->set_final(*$3);
}
......
......@@ -59,6 +59,10 @@ eol \n|\r|\n\r|\r\n
/* Rules for the automaton definitions part. */
<INITIAL>"=" return token::EQ;
<IINTIAL>"accept" return token::ACC;
<INITIAL>[tT][rR][uU][eE] {
return token::CONST_TRUE;
}
<INITIAL>"(" return token::LPAREN;
<INITIAL>")" return token::RPAREN;
<INITIAL>"%" BEGIN(formula);
......
......@@ -23,7 +23,6 @@
# define SPOT_ELTLPARSE_PUBLIC_HH
# include "eltlast/formula.hh"
# include "eltlast/visitor.hh"
// Unfortunately Bison 2.3 uses the same guards in all parsers :(
# undef BISON_LOCATION_HH
# undef BISON_POSITION_HH
......
......@@ -4,9 +4,9 @@
set -e
cat >prelude <<EOF
S=(
X=(
0 1 \$0
= 1
accept 1
)
EOF
......@@ -15,13 +15,26 @@ include prelude
A=(
0 1 \$2
1 2 \$0
= 0
accept 0
)
%
A(1,a,a|b)&S(1)
A(1,a,a|b)&X(f)
EOF
run 0 ./acc input || exit 1
cat >input <<EOF
X=(
0 1 true
1 2 \$0
accept 2
)
U=(
0 0 \$0
0 1 \$1