{Coding in Promela}
1. Proctypes Actions:
int x = 15, y = 20;
int a = x, b = y;
/*parGCD2*/
active proctype Action1() {
do
:: a > b -> a = a - b
:: a == b -> break
od;
printf("Action1 terminating: GCD of %d and %d is equal to %d\n", x, y, a)
}
active proctype Action2() {
do
:: b > a -> b = b - a
:: a == b -> break
od;
printf("Action2 terminating: GCD of %d and %d is equal to %d\n", x, y, b)
}
2. Assertions: (2 methods of除法)
active proctype divide() {
int dividend = 15;
int divisor = 4;
int quotient, remainder;
assert (dividend >= 0 && divisor > 0);
quotient = 0;
remainder = dividend;
do
:: remainder >= divisor ->
quotient++;
remainder = remainder - divisor
:: else -> break
od;
printf("%d divided by %d = %d, remainder = %d\n",
dividend, divisor, quotient, remainder);
assert (0 <= remainder && remainder < divisor);
assert (dividend == quotient * divisor + remainder)
}
active proctype P() {
int dividend = 15, divisor = 4;
int quotient = 0, remainder = 0;
int n = dividend;
assert (dividend >= 0 && divisor > 0);
do
:: n != 0 ->
assert (dividend == quotient * divisor + remainder + n);
assert (0 <= remainder && remainder < divisor);
if
:: remainder + 1 == divisor ->
quotient++;
remainder = 0
:: else -> remainder++
fi;
n--
:: else -> break
od;
printf("%d divided by %d = %d, remainder = %d\n",
dividend, divisor, quotient, remainder);
assert (0 <= remainder && remainder < divisor);
assert (dividend == quotient * divisor + remainder)
}
3. Atomicity:
#include "for.h"
byte n = 0;
proctype P() {
byte temp;
for (i, 1, 10)
temp = n + 1;
n = temp
rof (i)
}
init {
atomic {
run P();
run P()
}
(_nr_pr == 1) ->
printf("The value is %d \n", n)
}
4. Channels:
chan request = [0] of { byte, chan };
chan reply [2] = [0] of { byte, byte };
/*array*/
active [2] proctype Server() {
byte client;
chan replyChannel;
end:
do
:: request ? client, replyChannel ->
printf("Client %d processed by server %d\n", client, _pid);
replyChannel ! _pid, client
od
}
active [2] proctype Client() {
byte server;
byte whichClient;
request ! _pid, reply[_pid-2];
reply[_pid-2] ? server, whichClient;
printf("Reply received from server %d by client %d\n",
server, _pid); assert(whichClient == _pid)
}
chan request = [0] of { byte, chan };
chan reply [4] = [0] of { byte, byte };
/*number*/
int numClients =0; // number of clients waiting for a response
active [2] proctype Server() {
byte client;
chan replyChannel;
end:
do
:: request ? client, replyChannel ->
printf("Client %d processed by server %d\n", client, _pid);
replyChannel ! _pid, client
od
}
active [4] proctype Client() {
byte server;
request ! _pid, reply[_pid-2];
numClients++;
assert (numClients <= 2);
numClients--;
reply[_pid-2]? server, _
}
chan request = [4] of { byte };
chan reply = [4] of { byte, byte };
/*randRec*/
active [2] proctype Server() {
byte client;
end:
do
:: request ? client -> printf("Client %d processed by server %d\n", client, _pid);
reply ! _pid, client
od
}
active [4] proctype Client() {
byte server;
request ! _pid;
reply ?? server, eval(_pid);
printf("Reply received from server %d by client %d\n", server, _pid)
}
5. CrtiticalSection and Datarace:
bool wantP = false, wantQ = false;
int turn =0;
/*peterson*/
active proctype P() {
NTS: printf("Noncritical section P\n");
wantP = true; turn = 1;
TS: !wantQ || turn == 0;
CS: printf("Critical section P\n");
wantP = false;
progress: goto NTS;
}
active proctype Q() {
NTS: printf("Noncritical section Q\n");
wantQ = true; turn =0;
TS: !wantP || turn == 1;
CS: printf("Critical section Q\n");
wantQ = false;
progress: goto NTS;
}
#define pInCS (P@CS)
#define qInCS (Q@CS)
#define pTrying (P@TS)
#define qTrying (Q@TS)
#define mutex (!(pInCS && qInCS))
#define progress4P (pTrying -> <> pInCS)
#define progress4Q (qTrying -> <> qInCS)
//ltl safety { [] mutex }
//ltl progP { [] progress4P}
ltl progQ { [] progress4Q}
byte n = 0;
/*datarace #1*/
#define Two (n == 2)
#define Terminated (np_ == 0)
/*
It is always the case that when terminated, n is equal to 2.
ltl { [] (Terminated -> Two) }
*/
ltl { [] (Terminated -> Two) }
active proctype P() {
byte temp;
temp = n + 1;
n = temp;
printf("Process P, n = %d\n", n)
}
active proctype Q() {
byte temp;
temp = n + 1;
n = temp;
printf("Process Q, n = %d\n", n)
}
#include "for.h"
byte n = 0;
/*datarace #2*/
proctype P() {
byte temp;
for (i, 1, 10)
temp = n + 1;
n = temp
rof (i)
}
init {
atomic {
run P();
run P()
}
(_nr_pr == 1) ->
printf("The value is %d \n", n)
}
6. mtype:
mtype = { red, yellow, green };
mtype light = green;
/*mtype example#1*/
active proctype P() {
do
:: if
:: light == red -> light = green
:: light == yellow -> light = red
:: light == green -> light = yellow
fi;
printf("The light is now %e\n", light)
od
}
mtype = { red, yellow, green };
mtype = { green_and_yellow, yellow_and_red };
mtype light = green;
/*mtype example#2*/
active proctype P() {
do
:: if
:: light == red -> light = yellow_and_red
:: light == yellow_and_red -> light = green
:: light == green -> light = green_and_yellow
:: light == green_and_yellow -> light = red
fi;
printf("The light is now %e\n", light)
od
}