Tutorial

Tutorial

Running example: communication through unreliable media

Let us describe a small example. We will model a client and a server which communicate through a two unreliable channels (a channel for each way). The client has to send a sequence of M different requests to the server. The server treat the request and send an acknowlegdement. If there is a failure (we suppose that the client can detect it), the client can retry twice to send the request. On completion, the sender emit the message CORR, otherwise the message ERR.

Global declarations

We first declare the set of channels:


channel
        S_send,S_receive,S_lost,
        A_send,A_receive,A_lost,
        START,CORR,ERR;

If we had global variables, we would also declare them here.

The two communication media

Then we define the SendLine and AckLine processes. The keyword sync allows to define the set of channels on which the process synchronize. init defines the root state(s). The sign # is used to refer to a location name. Then the list of locations, together with their outgoing transitions, is described. when introduces the possible guard on variables, sync specifies a possible synchronization channel for the transition, and goto the destination location or the distribution over several destination locations.


process SendLine {
  sync
        S_send,S_receive,S_lost;
  init
        #idle;

  loc idle:
    when true sync S_send goto { sent 0.8; lost 0.2 };
  loc sent:
    when true sync S_receive goto idle;
  loc lost:
    when true sync S_lost goto idle;
}

process AckLine {
  sync
        A_send,A_receive,A_lost;
  init
        #idle;

  loc idle:
    when true sync A_send goto { sent 0.9; lost 0.1 };
  loc sent:
    when true sync A_receive goto idle;
  loc lost:
    when true sync A_lost goto idle;
}

The Client process

The more complex process is the Client process. This process owns two local variables. Their type is uint(2), which means: 2-bits unsigned integers. Here the destination locations are possibly followed by an assign instruction which specifies the new values of some variables


process Client { 
  sync
        S_send,S_lost,A_lost,A_receive,
        START,CORR,ERR;
  var
        n,msg : uint(2);
  init
        #idle;

  loc idle:
    when true sync START goto msg assign { msg := uint(2)0 };
  loc msg:
    when true sync S_send goto wait assign { n := uint(2)0 };
  loc wait:
    when msg < uint(2)3 sync A_receive goto msg assign { msg := msg + uint(2)1 };
    when msg = uint(2)3 sync A_receive goto end;
    when true sync S_lost goto retry;
    when true sync A_lost goto retry;
  loc retry:
    when n < uint(2)3 sync S_send goto wait assign { n := n + uint(2)1 };
    when n = uint(2)3 sync ERR goto idle;
  loc end:
    when true sync CORR goto idle;
}

The Server process

Last, we have the (dummy) Server process:


process Server {
  sync
        S_receive,A_send,A_receive,A_lost;
  init
        #idle;

  loc idle:
    when true sync S_receive goto task;
  loc task:
    when true sync A_send goto wait;
  loc wait:
    when true sync A_receive goto idle;
    when true sync A_lost goto idle;
}

The property

Now we specify the property. We refer to locations and local variables by prefixing them with the name of the owner process. system the set of processes that are composed in parallel, and initial and final two sets of states. Basically, we want to check properties about the probability to reach a final state from an initial state during an execution of the system.


system SendLine,AckLine,Client,Server;
initial #Client.idle;
final #Client.end;

In this case, what is the probability to successfully send all the messages without any transmission error ?

Verification

We will use for this property the version of the tool which uses the CDDLIB LP solver. Let us type probr.opt -exact -goal s0.5 example.prob. We get the following output:

- Syntaxical analysis
- Semantic analysis, transformation into Bdds
** computing processes and expressions
** Boolean composition
** Boolean analysis
    Initially: 15 state variables, 32768 states
    relation: 396 nodes
    Reordering...
    Reachability analysis from init: 184 states, 35 nodes
    Reachability analysis from initial: 184 states, 35 nodes
    psup0: 0 states, 1 nodes
    Extending final states
    All reachable initial states are also pinf1; pinf = psup = 1.0
Example: (SendLine.loc=idle)(AckLine.loc=idle)(Client.loc=idle)
         (Server.loc=idle)

Note: Using Rapture 2.0.0, one gets a slightly different output than the one displayed above, but the essential results remain the same.

The tool discovered by discrete fixpoint analysis that every initial state has a probability 1 to lead eventually to a final state. After some reflexion, it appears that it is perfectly right: as the sender process can send a new message after having emitted ERR and as the failure probability is strictly less than 1, you eventually lead to a final state with probability 1.

What we actually want to check is the probability to send correctly one message. Let's add the following process into the system.


process Sync2 {
  sync
        START,CORR;
  init
        #idle;

  loc idle:
    when true sync START goto run;
  loc run:
    when true sync CORR goto end;
  loc end:
}

and let's write the new property


system SendLine,AckLine,Client,Server,Sync2;
initial #Sync2.idle;
final #Sync2.end;

We get the following output:

- Syntaxical analysis
- Semantic analysis, transformation into Bdds
** computing processes and expressions
** Boolean composition
** Boolean analysis
    Initially: 17 state variables, 131072 states
    relation: 469 nodes
    Reordering...
    Reachability analysis from init: 192 states, 49 nodes
    Reachability analysis from initial: 192 states, 49 nodes
    psup0: 16 states, 31 nodes
    Extending final states
    Second reachability analysis from initial: 176 states, 40 nodes
    Non-sink state space: 164 states, 57 nodes
    Psup=1: 4 states
in 0.08 seconds
** computing global probabilistic transition function
** size of the transition function: 319 nodes, 1550 paths, 6 leaves
System build and analysed (Boolean analysis) in 0.12 seconds

Building initial partition in 0.01 seconds

Step 1, automaton has 10 locations and 12 nails, 5420 bytes
essential automaton has 5 locations and 7 nails
Computing psup: discrete analysis, 1.0
pinf=-inf  psup=1  diff=inf
analysis in 0 seconds
refining in 0.01 seconds

Step 2, automaton has 16 locations and 22 nails, 9564 bytes
essential automaton has 9 locations and 15 nails
Computing psup: discrete analysis, 1.0
pinf=-inf  psup=1  diff=inf
analysis in 0 seconds
refining in 0.03 seconds

Step 3, automaton has 29 locations and 38 nails, 15784 bytes
essential automaton has 20 locations and 29 nails
Computing psup: discrete analysis, 1.0
pinf=-inf  psup=1  diff=inf
analysis in 0 seconds
refining in 0.02 seconds

Step 4, automaton has 44 locations and 48 nails, 20380 bytes
essential automaton has 21 locations and 25 nails
Computing psup: 19 variables, 25 constraints, 13 equalities;
pinf=-inf  psup=0.990478425818  diff=inf
analysis in 0.03 seconds
refining in 0.03 seconds

Step 5, automaton has 68 locations and 70 nails, 29748 bytes
essential automaton has 30 locations and 32 nails
Computing psup: 28 variables, 32 constraints, 24 equalities;
pinf=-inf  psup=0.981673428381  diff=inf
analysis in 0.02 seconds
refining in 0.02 seconds

Step 6, automaton has 78 locations and 76 nails, 32068 bytes
essential automaton has 34 locations and 32 nails
Computing psup: 32 variables, 32 constraints, 32 equalities;
pinf=-inf  psup=0.975639513753  diff=inf
analysis in 0.01 seconds
refining in 0 seconds
** Failure **
After 6 steps and 13 divisions, final automaton has 78 locations
pinf=-inf psup=0.975639513753 diff=inf
Times in seconds:
  building: 0.12
  analysis: 0.18 (numerical computations: 0.06; refinement: 0.12)

The property is false, because the Psup <= 0.5 on the stabilized partition of the system. As every member of this partition are bisimulation equivalence classes, we get that Psup=.975639513753 on the concrete system.


Bertrand Jeannet, July 18, 2006 - Updated on March 14, 2017 by Hubert Garavel and Jean-Philippe Gros

Tutorial