Commit 5aba246f authored by Alexandre Duret-Lutz's avatar Alexandre Duret-Lutz

org: syntax-highlight the HOA outputs

* elisp/hoa-mode.el, elisp/Makefile.am, elisp/README: New files.
* debian/copyright, configure.ac, README, Makefile.am: Adjust.
* doc/org/init.el.in: Adjust to load hoa-mode.el.
* doc/org/spot.css: Add entries for HOA mode.
* doc/org/hoa.org, doc/org/ltldo.org, doc/org/oaut.org,
doc/org/tut20.org, doc/org/tut21.org, doc/org/tut22.org,
doc/org/tut30.org: Make the HOA outputs as HOA.
parent d46da963
......@@ -21,14 +21,14 @@
## along with this program. If not, see <http://www.gnu.org/licenses/>.
if NEVER
# For Automake a conditional directory
# For Automake a, conditional directory
# is conditionally built, but unconditionally distributed.
# So using NEVER here ensures that `make all' will not
# recurse in bench/, but `make dist' will.
NEVER_BENCH = bench
NEVER_SUBDIRS = bench elisp
endif
SUBDIRS = buddy lib src wrap ltdl iface doc $(NEVER_BENCH)
SUBDIRS = buddy lib src wrap ltdl iface doc $(NEVER_SUBDIRS)
UTF8 = utf8/doc/ReleaseNotes utf8/doc/utf8cpp.html utf8/utf8.h \
utf8/utf8/checked.h utf8/utf8/core.h utf8/utf8/unchecked.h
......
......@@ -180,6 +180,7 @@ buddy/ A customized version of BuDDy 2.3 (a BDD library).
ltdl/ Libtool's portable dlopen() wrapper library.
lib/ Gnulib's portability modules.
utf8/ Nemanja Trifunovic's utf-8 routines.
elisp/ Related emacs modes, used for building the documentation.
Build-system stuff
------------------
......
......@@ -197,6 +197,7 @@ AC_CONFIG_FILES([
doc/tl/Makefile
doc/org/.dir-locals.el
doc/org/init.el
elisp/Makefile
iface/ltsmin/defs
iface/ltsmin/Makefile
iface/Makefile
......
......@@ -125,6 +125,25 @@ Copyright: (unknown) D A Gwyn
License: public-domain
(Mostly) portable public-domain implementation -- D A Gwyn
Files: elisp/hoa-mode.el
Copyright: 2015 Alexandre Duret-Lutz
License: GPL-3+
This program 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 3 of the License, or
(at your option) any later version.
.
This program 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 this program. If not, see <http://www.gnu.org/licenses/>.
.
On Debian systems, the complete text of the GNU General
Public License version 3 can be found in "/usr/share/common-licenses/GPL-3".
Files: debian/*
Copyright: 2015 Laboratoire de Recherche et Développement de l'Epita (LRDE)
License: GPL-3+
......
......@@ -139,12 +139,12 @@ EOF
#+RESULTS:
#+BEGIN_SRC sh :results verbatim :exports results
#+BEGIN_SRC sh :results verbatim :exports results :wrap SRC hoa
sed -n '/--BODY/,/--END/p' stvstracc.hoa | grep -v -- --
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
/* state-based acceptance */
State: 0 {0 1}
[0&!1] 0
......@@ -158,16 +158,16 @@ State: 1 {0}
State: 2
[!0] 1 {0}
[0] 2 {1}
#+end_example
#+END_SRC
will always be stored as a TωA with this transition structure:
#+BEGIN_SRC sh :results verbatim :exports results
#+BEGIN_SRC sh :results verbatim :exports results :wrap SRC hoa
autfilt -Ht stvstracc.hoa | sed -n '/--BODY/,/--END/p' | grep -v -- --
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
State: 0
[0&!1] 0 {0 1}
[0&1] 1 {0 1}
......@@ -178,7 +178,7 @@ State: 1
State: 2
[!0] 1 {0}
[0] 2 {1}
#+end_example
#+END_SRC
#+BEGIN_SRC sh :results silent :exports results
rm -f stvstracc.hoa
......@@ -201,8 +201,8 @@ For instance in the following automaton, the outgoing transitions of
each states belong to the same sets:
#+NAME: state-based-example
#+BEGIN_SRC sh :results verbatim :exports both
cat >sba.hoa <<EOF
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
cat >sba.hoa <<EOF_HOA
HOA: v1
States: 3
Start: 0
......@@ -220,14 +220,14 @@ State: 2
[!0] 1 {0 1}
[0] 2 {0 1}
--END--
EOF
EOF_HOA
autfilt -H sba.hoa
#+END_SRC
so the HOA output of =autfilt= automatically uses state-based acceptance:
#+RESULTS: state-based-example
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
States: 3
Start: 0
......@@ -247,7 +247,7 @@ State: 2 {0 1}
[!0] 1
[0] 2
--END--
#+end_example
#+END_SRC
The rational for this automatic switch to state-based acceptance is as follows:
- Tools that support transition-based acceptance can easily see
......@@ -265,12 +265,12 @@ Nevertheless, should you really insist on having an output with
transition-based acceptance, you can do so by passing the option =t=
to the HOA printer:
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
autfilt -Ht sba.hoa
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
States: 3
Start: 0
......@@ -290,7 +290,7 @@ State: 2
[!0] 1 {0 1}
[0] 2 {0 1}
--END--
#+end_example
#+END_SRC
#+BEGIN_SRC sh :results silent :exports results
rm sba.hoa
......@@ -302,12 +302,12 @@ format to prevents mixing the two: if you use =-Hm=, the decision of
using state or transition-based acceptance will be made for each state
separately. For instance:
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
ltl2tgba -Hm 'GFa | Fb'
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
name: "F(b | GFa)"
States: 3
......@@ -327,7 +327,7 @@ State: 2
[1] 2 {0}
[!1] 2
--END--
#+end_example
#+END_SRC
So far we have discussed transforming state-based acceptance into
......@@ -342,12 +342,12 @@ when necessary. Most tools have a =-S= option (or
=--state-based-acceptance=) for this purpose. Compare the following
output with the previous one.
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
ltl2tgba -S -Hm 'GFa | Fb'
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
name: "F(b | GFa)"
States: 4
......@@ -370,7 +370,7 @@ State: 3
[1] 2
[!1] 3
--END--
#+end_example
#+END_SRC
** Generic acceptance
......@@ -431,7 +431,7 @@ In the following example, you can see =autfilt= removing the duplicate
Rabin pair, and reordering the remaining pair to fit the syntax
corresponding to =Rabin 1=.
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
autfilt -H <<EOF
HOA: v1
States: 3
......@@ -454,7 +454,7 @@ EOF
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
States: 3
Start: 0
......@@ -474,9 +474,7 @@ State: 2 {0 1}
[!0] 1
[0] 2
--END--
#+end_example
#+END_SRC
Internally, the acceptance condition is stored as an array in reverse
polish notation, and the primitives =Inf= and =Fin= are actually
......@@ -500,12 +498,14 @@ When you look at an acceptance condition output by Spot, you can
actually spot the terms that have been grouped together internally by
looking at the spacing around operators =&= and =|=. For instance:
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
randaut -A"Fin(0)|Fin(1)|Fin(2)&Fin(3)&Inf(4)&Inf(5)" -H 0 | grep Acceptance:
#+END_SRC
#+RESULTS:
: Acceptance: 6 (Fin(0)|Fin(1)) | (Fin(2) & Fin(3) & (Inf(4)&Inf(5)))
#+BEGIN_SRC hoa
Acceptance: 6 (Fin(0)|Fin(1)) | (Fin(2) & Fin(3) & (Inf(4)&Inf(5)))
#+END_SRC
Here =Fin(0)|Fin(1)= is actually a single internal term =Fin({0,1})=,
and likewise for =Inf(4)&Inf(5)=.
......@@ -611,7 +611,7 @@ They are currently two named properties related to the HOA format.
You can see these properties being preserved when an automaton is read and then immediately output:
#+NAME: hello-world
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
cat >hw.hoa <<EOF
HOA: v1
name: "hello world!"
......@@ -636,7 +636,7 @@ autfilt -H hw.hoa
#+END_SRC
#+RESULTS: hello-world
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
name: "hello world!"
States: 3
......@@ -657,7 +657,7 @@ State: 2 "so am I" {0 1}
[!0] 1
[0] 2
--END--
#+end_example
#+END_SRC
However if =autfilt= performs some transformation, and actually has to
construct a new automaton, those properties will not be quarried over
......@@ -670,32 +670,32 @@ the old states and the new ones.
Here is for instance the result when =autfilt= is instructed to
simplify the automaton:
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
autfilt -H --small hw.hoa
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
States: 3
Start: 0
AP: 2 "a" "b"
acc-name: Buchi
Acceptance: 1 Inf(0)
properties: trans-labels explicit-labels trans-acc deterministic
properties: trans-labels explicit-labels state-acc deterministic
--BODY--
State: 0
[0&!1] 0
[0&1] 1 {0}
[!0] 2 {0}
[0&1] 1
[!0] 2
State: 1
[0&!1] 1
[0&1] 2
State: 2
[!0] 1 {0}
[0] 2 {0}
State: 2 {0}
[!0] 1
[0] 2
--END--
#+end_example
#+END_SRC
Note that if the name of the automaton is important to you, it can be
......@@ -703,12 +703,12 @@ fixed via the =--name= option. For instance =--name=%M= will
construct the new name by simply copying the one of the original
automaton.
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
autfilt -H --small hw.hoa --name=%M
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
name: "hello world!"
States: 3
......@@ -716,20 +716,20 @@ Start: 0
AP: 2 "a" "b"
acc-name: Buchi
Acceptance: 1 Inf(0)
properties: trans-labels explicit-labels trans-acc deterministic
properties: trans-labels explicit-labels state-acc deterministic
--BODY--
State: 0
[0&!1] 0
[0&1] 1 {0}
[!0] 2 {0}
[0&1] 1
[!0] 2
State: 1
[0&!1] 1
[0&1] 2
State: 2
[!0] 1 {0}
[0] 2 {0}
State: 2 {0}
[!0] 1
[0] 2
--END--
#+end_example
#+END_SRC
The page about [[file:oaut.org][common output option for automata]] has a section showing
how =--name= can be used to construct complex pipelines with automata that
......@@ -748,12 +748,12 @@ in the HOA format, and then read those automata with =autfilt= to
randomize the order of their transitions and states before printing
them in HOA format.
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
genltl --and-gf=1..3 | ltl2tgba -B -F- -H | autfilt --randomize -H
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
name: "GFp1"
States: 2
......@@ -762,7 +762,7 @@ AP: 1 "p1"
acc-name: Buchi
Acceptance: 1 Inf(0)
properties: trans-labels explicit-labels state-acc complete
properties: deterministic
properties: deterministic stutter-invariant
--BODY--
State: 0
[0] 1
......@@ -779,7 +779,7 @@ AP: 2 "p1" "p2"
acc-name: Buchi
Acceptance: 1 Inf(0)
properties: trans-labels explicit-labels state-acc complete
properties: deterministic
properties: deterministic stutter-invariant
--BODY--
State: 0
[!0&1] 2
......@@ -801,7 +801,7 @@ AP: 3 "p1" "p2" "p3"
acc-name: Buchi
Acceptance: 1 Inf(0)
properties: trans-labels explicit-labels state-acc complete
properties: deterministic
properties: deterministic stutter-invariant
--BODY--
State: 0
[!2] 0
......@@ -821,7 +821,7 @@ State: 3
[0] 1
[!0] 3
--END--
#+end_example
#+END_SRC
It should be noted that the HOA parser is less efficient when it reads
......
;; htmlize is not always in the load-path. On Debian it can be found here.
(setq load-path (cons "/usr/share/emacs/site-lisp/emacs-goodies-el" load-path))
(setq load-path (append '("@abs_top_srcdir@/elisp/" ; for hoa-mode.el
;; htmlize is not always in the load-path.
;; On Debian it can be found here.
"/usr/share/emacs/site-lisp/emacs-goodies-el")
load-path))
(or (require 'org-publish nil t) ; Org 7
(require 'ox-publish)) ; Org 8
(require 'org-install)
(require 'hoa-mode)
(print (concat "Org " (org-version)))
(setq org-export-htmlize-output-type 'css)
......
......@@ -128,19 +128,20 @@ Here is another example, where we use Spin to produce two automata in
the [[http://adl.github.io/hoaf/][HOA format]]. Spin has no support for HOA, but =ltldo= simply
converts the never claim produced by =spin= into this format.
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
ltldo -f a -f GFa 'spin -f %s>%O' -H
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
States: 2
Start: 0
AP: 1 "a"
acc-name: Buchi
Acceptance: 1 Inf(0)
properties: trans-labels explicit-labels state-acc deterministic
properties: trans-labels explicit-labels state-acc colored
properties: deterministic
--BODY--
State: 0 {0}
[0] 1
......@@ -161,7 +162,7 @@ State: 0
State: 1 {0}
[t] 0
--END--
#+end_example
#+END_SRC
Again, using the shorthands defined below, the previous command can be
simplified to just this:
......@@ -405,34 +406,35 @@ an LTL formula). In the following example, you can see that the
automaton uses the atomic proposition =Error=, but its name contains a
reference to =p0=.
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
ltldo 'ltl3ba -H' -f '[]!Error' -H
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
name: "BA for ([](!(p0)))"
name: "BA for [](!(p0))"
States: 1
Start: 0
AP: 1 "Error"
acc-name: Buchi
Acceptance: 1 Inf(0)
properties: trans-labels explicit-labels state-acc deterministic
properties: trans-labels explicit-labels state-acc colored
properties: deterministic
--BODY--
State: 0 "accept_init" {0}
[!0] 0
--END--
#+end_example
#+END_SRC
If this is a problem, you can always force a new name with the
=--name= option:
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
ltldo 'ltl3ba -H' -f '[]!Error' -H --name='BA for %f'
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
name: "BA for []!Error"
States: 1
......@@ -440,12 +442,13 @@ Start: 0
AP: 1 "Error"
acc-name: Buchi
Acceptance: 1 Inf(0)
properties: trans-labels explicit-labels state-acc deterministic
properties: trans-labels explicit-labels state-acc colored
properties: deterministic
--BODY--
State: 0 "accept_init" {0}
[!0] 0
--END--
#+end_example
#+END_SRC
* Controlling and measuring time
......
......@@ -71,11 +71,11 @@ format can be found on a [[file:hoa.org][separate page]].)
Here is an example where [[file:ltl2tgba.org][=ltl2tgba=]] is used to construct two automata:
one for =a U b= and one for =(Ga -> Gb) W c=.
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
ltl2tgba -H 'a U b' '(Ga -> Gb) W c'
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
name: "a U b"
States: 2
......@@ -84,6 +84,7 @@ AP: 2 "a" "b"
acc-name: Buchi
Acceptance: 1 Inf(0)
properties: trans-labels explicit-labels state-acc deterministic
properties: stutter-invariant terminal
--BODY--
State: 0 {0}
[t] 0
......@@ -98,7 +99,7 @@ Start: 1
AP: 3 "b" "a" "c"
acc-name: Buchi
Acceptance: 1 Inf(0)
properties: trans-labels explicit-labels trans-acc
properties: trans-labels explicit-labels trans-acc stutter-invariant
--BODY--
State: 0
[0] 0 {0}
......@@ -118,7 +119,7 @@ State: 4
[!1] 3
[1] 4
--END--
#+end_example
#+END_SRC
The above output contains two automata, named after the formulas they
represent. Here is a picture of these two automata:
......@@ -301,36 +302,37 @@ to use state-based acceptance whenever possible. Option =t= forces
transition-based acceptance. For instance compare this output to the
previous one:
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
ltl2tgba -Ht 'a U b'
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
name: "a U b"
States: 2
Start: 0
Start: 1
AP: 2 "a" "b"
acc-name: Buchi
Acceptance: 1 Inf(0)
properties: trans-labels explicit-labels trans-acc deterministic
properties: stutter-invariant terminal
--BODY--
State: 0
[1] 1
[0&!1] 0
[t] 0 {0}
State: 1
[t] 1 {0}
[1] 0
[0&!1] 1
--END--
#+end_example
#+END_SRC
Option =m= uses mixed acceptance, i.e, some states might use
state-based acceptance while other will not:
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
ltl2tgba -Hm '(Ga -> Gb) W c'
#+END_SRC
#+RESULTS:
#+begin_example
#+BEGIN_SRC hoa
HOA: v1
name: "(Gb | F!a) W c"
States: 5
......@@ -338,7 +340,7 @@ Start: 1
AP: 3 "b" "a" "c"
acc-name: Buchi
Acceptance: 1 Inf(0)
properties: trans-labels explicit-labels
properties: trans-labels explicit-labels stutter-invariant
--BODY--
State: 0 {0}
[0] 0
......@@ -358,7 +360,7 @@ State: 4
[!1] 3
[1] 4
--END--
#+end_example
#+END_SRC
It is also possible to output each automaton on a single line, in case
......@@ -366,12 +368,14 @@ the result should be used with line-based tools or embedded into a CSV
file... Here is an example using both transition-based acceptance,
and single-line output:
#+BEGIN_SRC sh :results verbatim :exports both
#+BEGIN_SRC sh :results verbatim :exports both :wrap SRC hoa
ltl2tgba -Htl 'a U b' '(Ga -> Gb) W c'
#+END_SRC
#+RESULTS:
: HOA: v1 name: "a U b" States: 2 Start: 1 AP: 2 "a" "b" acc-name: Buchi Acceptance: 1 Inf(0) properties: trans-labels explicit-labels trans-acc deterministic --BODY-- State: 0 [t] 0 {0} State: 1 [1] 0 [0&!1] 1 --END--
: HOA: v1 name: "(Gb | F!a) W c" States: 5 Start: 1 AP: 3 "b" "a" "c" acc-name: Buchi Acceptance: 1 Inf(0) properties: trans-labels explicit-labels trans-acc --BODY-- State: 0 [0] 0 {0} State: 1 [0&1&!2] 0 [!1&!2] 1 {0} [1&!2] 2 [2] 3 State: 2 [!1&!2] 1 {0} [1&!2] 2 [!1&2] 3 [1&2] 4 State: 3 [t] 3 {0} State: 4 [!1] 3 [1] 4 --END--
#+BEGIN_SRC hoa
HOA: v1 name: "a U b" States: 2 Start: 1 AP: 2 "a" "b" acc-name: Buchi Acceptance: 1 Inf(0) properties: trans-labels explicit-labels trans-acc deterministic stutter-invariant terminal --BODY-- State: 0 [t] 0 {0} State: 1 [1] 0 [0&!1] 1 --END--
HOA: v1 name: "(Gb | F!a) W c" States: 5 Start: 1 AP: 3 "b" "a" "c" acc-name: Buchi Acceptance: 1 Inf(0) properties: trans-labels explicit-labels trans-acc stutter-invariant --BODY-- State: 0 [0] 0 {0} State: 1 [0&1&!2] 0 [!1&!2] 1 {0} [1&!2] 2 [2] 3 State: 2 [!1&!2] 1 {0} [1&!2] 2 [!1&2] 3 [1&2] 4 State: 3 [t] 3 {0} State: 4 [!1] 3 [1] 4 --END--
#+END_SRC
* LBTT output
......
......@@ -18,8 +18,10 @@ body a{color:#008181}
div#postamble{visibility:hidden}
.outline-2 h2{border-bottom-style:solid;border-color:#ffe35e}
pre.src{padding-top:8px;border-left-style:solid;border-color:#00adad;overflow:auto}
pre.src-hoa{padding-top:8px;border-left-style:solid;border-color:#d70079;overflow:auto}
pre.example{border-left-style:solid;border-color:#d70079}
pre.src:before{border:none;border-bottom-style:solid;border-color:#00adad}
pre.src:before{border:none;border-bottom-style:solid;border-color:#00adad;top:0px;}
pre.src-hoa:before{content:'HOA';border:none;border-bottom-style:solid;border-color:#d70079;overflow:auto}
img{max-width:100%}
@media screen{
#table-of-contents{position:fixed;right:0em;top:0em;max-width:50%;max-height:80%;overflow:auto;z-index:10}
......@@ -34,7 +36,14 @@ img{max-width:100%}
.org-builtin{font-weight:bold}
.org-preprocessor{font-weight:bold}
.org-string{font-weight:bold;color:#00adad}
.src-hoa .org-string{font-weight:bold;color:#d70079}
.org-function-name{font-weight:bold;color:#d70079}
.org-type{font-weight:bold;color:#00adad}
.org-comment-delimiter{font-weight:bold;color:#a13672}
.org-comment{font-style:italic;color:#a13672}
.org-hoa-keyword{font-weight:bold}
.org-hoa-builtin{font-weight:bold}
.org-hoa-acceptance-set{font-weight:bold}
.org-hoa-header-uppercase{font-weight:bold;color:#00adad}
.org-hoa-header-lowercase{color:#00adad}
.org-hoa-ap-number{color:#d70079}
......@@ -52,12 +52,12 @@ This is very simple: [[file:autfilt.org][=autfilt=]] can read automata in any of
supported formats, so all we have to do is to request the HOA output