��ʸ��ϡ�Spin Model Checker �θ��������� http://spinroot.com �ˤ��� Basic Spin Manual ������������ΤǤ�������ʸ��ϡ�Gerard J. Holzmann �˵��Ĥ����Ƹ������Ƥ��ޤ��������������ʤɤ���ޤ����顢https://github.com/masateruk/BasicSpinManual�ˤ�Issue�ޤ���PR�ˤƤ���𤤤�������ȹ����Ǥ���

���� Masateru Kawaguchi

Basic Spin Manual

Spin ���¹ԥ����ƥ����Ǥ�ǡ����̿��ץ��ȥ���ˤ�����Ū������򸡾ڤ���ġ���Ǥ��������ƥ�ο����񤤤ϡ�Promela��Process Meta Language�ˤȸƤФ���ǥ�󥰸���ˤ�äƵ��Ҥ��ޤ������θ���Ǥϡ��¹ԥץ�������ưŪ�����򵭽Ҥ�������Ǥ��ޤ�������ͥ��𤷤���å������̿���Ʊ���̿��ʥ��ǥ֡ˡ���Ʊ���̿��ʥ��塼�ˤ��Хåե���󥰡ˤ�ξ���򵭽Ҥ�������Ǥ��ޤ���

�����ϡ�Spin ��Ȥ� Promela �ǵ��Ҥ��������ƥ������ॷ�ߥ�졼����󤷤��ꡢ�ޤ���Promela �ǵ��Ҥ�����ǥ뤫�� C ����θ��ڥץ��������������������ƥ���������θ��ڤ�Ԥ������Ǥ��ޤ������ߥ塼�졼�����両�ڤδ֡�Spin �ϥǥåɥ��å����ʤ�����տޤ��ʤ���å�������������ʤ������ޤ��¹Ԥ��Ƥ��ʤ������ɤ��ʤ������ʤɥ����å����ޤ������ڥץ������Ϥޤ������ƥ�����Ѿ�郎�ݻ�����Ƥ��뤫�ɤ����򸡾ڤ����ꡢ�Υ�ץ����쥹���������non-progress execution cycles�ˤ��ʤ������������ꡢ��������������Linear Temporal Logic�ˤǵ��Ҥ�������˰�ȿ���Ƥ��ʤ����򸡾ڤ��ޤ���

���ڥץ������ϸ�Ψ���ˤ����졢��������̤�¿������ޤ���Spin �ˤ����õ�����ڤη�̡������ϡ������ƥ�ο����񤤤˥��顼���ʤ����ɤ����ˤĤ��ơ�����Ū��΢�դ����줿�ξڤ����뤳�Ȥ��Ǥ���ΤǤ�������ԥ塼���Υ꥽���������¤����̾���Բ�ǽ�Ȥ�����礭�ʥ����ƥ�θ��ڤ⡢"�ӥåȾ��ֶ��ּ�ˡ" �Ȥ������󵻽Ѥ����θ��ڤ��ǽ�Ȥ��Ƥ��ޤ������μ�ˡ�Ǥϡ������Ѥ�Ǿ��¤��ޤ��ʤ��顢��ã��ǽ�ʳƾ��֤���ӥåȤ˰��̤��뤳�Ȥ��Ǥ��ޤ���

���Υ����� 1 ���Ǥ� Promela �ξҲ���� 2 ���Ǥ� Spin �λ�����ˡ�ˤĤ��ƤȤꤢ���ޤ���Promela �δʷ�ʥ�ե���󥹤��������ˤ���ޤ�����Ͽ�Ǥϡ������Ĥ�����򼨤���Spin �Ǹ��ڤ��뤿��� Promela ��Ȥä�����Ū�ʥ�ǥ�κ�����ˡ�ˤĤ����������ޤ���

���Υޥ˥奢��Ǥϡ�Spin �μ�����ʬ�ΤߤˤĤ��Ƶ������ޤ���Promela ����γ�ĥ��ġ���κǶ�ΥС������˴ؤ�������ˤĤ��ƤϿ���Ƥ��ޤ���ʾܤ����ϡ����Υޥ˥奢��κǸ�򻲾Ȥ��Ƥ��������ˡ��ޤ���LTL �ǵ��Ҥ����������Ѥ������ڤˤĤ��Ƥ�������ޤ���

��ǥ�󥰸����Modeling Language��

Promela �ϸ����ѤΥ�ǥ�󥰸���Ǥ������θ���Ǥϡ����ڤ����Ǵؿ��Τʤ��ץ���������ߺ��Ѥ�ξݤ���ݲ������ץ��ȥ���ʤޤ��ϡ�����Ū��ʬ�������ƥ�ˤ򵭽Ҥ��뤳�Ȥ��Ǥ��ޤ���Spin �λ�����Ū�ϡ������Ĥ�����ͳ�ˤ�굿�路���Ȼפ��뾯���Υץ������ο����񤤤򸡾ڤ��뤳�ȤǤ��� Promela �Ǵؿ��Τ��뿶������ʬ�ˤĤ��Ƶ��Ҥ������ڤ��ޤ���Promela ��ǥ���ʳ�Ū�˾ܺٲ����Ƥ�������Ϣ�Υ��ƥåפ�ФƸ��ڤ򴰷뤵���ޤ����ơ��Υ�ǥ���Ф����Ķ��ˤ�äưۤʤ��͡��ʲ���ʤ��Ȥ��С���å��������������Ȥ�����å���������ʣ����Ȥ��ˤ����ꤷ�ơ����ڤ��뤳�Ȥ��Ǥ��ޤ������١�Spin �ˤ����������ǥ���ۤ��뤳�Ȥ��Ǥ���С����θ�Υ�ǥ�κ����ȸ��ڤϡ����λ��¤��Ȥ˿ʤ�뤳�Ȥ��Ǥ��ޤ���

Promela ��ǥ���ץ���������å���������ͥ����ѿ�����ʤ�ޤ����ץ������ϥ������Х륪�֥������ȤǤ�����å���������ͥ���ѿ��ϥ������Х롢�⤷���ϡ��ץ�������������������������Ѥ��뤳�Ȥ��Ǥ��ޤ����ץ������Ͽ����񤤤򵭽Ҥ�������ͥ�ȥ������Х��ѿ��ϥץ�����������Ķ���������ޤ���

�¹Բ�ǽ����Executability��

Promela �ˤϡ�����ʸ�δ֤ˤʤˤ�㤤�Ϥ���ޤ���ñ�ȤΥ֡������ñ��ʸ�Ȥ��ư����ޤ�����ʸ�μ¹Ԥϡ������¹Բ�ǽ���ˤ��ޤ���ʸ�ϼ¹Բ�ǽ�Ǥ��뤫���¹��Բ�ǽ�ǥ֥��å�����뤫�Τɤ���ˤʤ�ޤ����¹Բ�ǽ���ϡ�Ʊ����Ȥ����Ū����ˡ�Ǥ����֥��å����줿�ץ������ϡ��¹Բ�ǽ�ˤʤ륤�٥�Ȥ�ȯ������Τ��Ԥ��ޤ������Ȥ��С��ʲ��Τ褦�˥ӥ����롼�פǽ������

	while (a != b)
		skip	/* wait for a==b */

Promela �Ǥϲ��Τ褦�˽񤤤ơ�Ʊ�����̤����뤳�Ȥ��Ǥ��ޤ���

	(a == b)

���ϡ����ξ�郎���������Ȥ��Τ߼¹Բ�ǽ�ˤʤ�ޤ����⤷����郎��������ʤ��Ȥ��ϡ����ξ�郎���������ޤǥ֥��å�����ޤ���

�������Х��ѿ��ϥ����ƥ�˴ؤ��륰�����Х�ʾ�����ݻ������ץ�������Υ��������ѿ��ϳƥץ������ξ��֤��ݻ����ޤ����ѿ�������ϡ�

	bool flag;
	int state;
	byte msg;

�Τ褦�˵��Ҥ��ޤ���������Τ褦�� Promela ���Ͱ�ΰۤʤ�3�Ĥ��������򥵥ݡ��Ȥ��Ƥ��ޤ����ѿ��Υ������פϡ��ץ�����������γ�¦��������줿��ΤϤ��٤ƥ������Х�ˤʤꡢ�ץ�����������������Τϥץ��������������ˤʤ�ޤ���

�ǡ�������Data Types��

������ɽ�ϡ�32-bit ��ɥ������Υ���ԥ塼���ˤ�������ܥǡ����������Υ��������ϰϤ�ޤȤ᤿��ΤǤ����ǡ��������ȡˡ�

Table 1 - Data Types
Typename
bit or bool
byte
short
int
C-equivalent
bit-field
uchar
short
int
Macro in limits.h
-
CHAR_BIT (width in bits)
SHRT_MIN..SHRT_MAX
INT_MIN..INT_MAX
Typical Range
0..1
0..255
-2^15 - 1 .. 2^15 - 1
-2^31 - 1 .. 2^31 - 1

bit �� bool �� 1 �ӥåȤξ����ɽ��Ʊ����Ǥ���byte �� 0 ���� 255 �ޤǤ��ͤ�Ȥ����ʤ��������Ǥ���shot �� int �Ϥ���餬�Ȥꤦ���ͤ��ϰϤ��㤦�����ǡ��Ȥ������դ������Ǥ���

mtype �ϡ�mtype = { ... } �Ȥ�����������������󷿤Ǥ�������ˤĤ��Ƥϡ���Ҥ��ޤ���

�����Array Variables��

�ѿ��ϡ�����Ȥ��Ƥ�����Ǥ��ޤ������Ȥ��С�

	byte state[N]

�����������硢state �� N �Ĥ� byte �����ѿ����Ĥ��Ȥ��Ǥ�������Ǥ�������γ����Ǥؤ�����������ͤλ��Ȥϡ�

	state[0] = state[3] + 5 * state[3*2/n]

�Τ褦�˵��Ҥ�������ǥå����ˤ��ѿ����������Ѥ�������Ǥ��ޤ�������Υ���ǥå����ϥ�ˡ����������ͤ�ɽ��������Ѥ��뤳�Ȥ��Ǥ��ޤ���������ϰϡ�0 .. N-1�˳��Υ���ǥå�������ꤷ����硢�����ͤ�̤����Ǥ��������Ƥ��ϥ�󥿥��२�顼�Ȥʤ�ޤ���¿��������� typedef ����Ѥ�����ˤ�����Ū������Ǥ��ޤ���WhatsNew.html 2.1.7 �Ỳ�ȡˡ�

�ѿ������ 2 �ĤΥ����פ�ʸ���֡�����ʸ������ʸ����򸫤Ƥ��ޤ���������������Ͼ���¹Բ�ǽ�Ǥ����ޤ������ʸ�Ϥ��줬��������Ƥ���Ȥ��Τ߼¹Բ�ǽ�Ǥ���

�ץ���������Process Types��

�ѿ������ͥ�ξ��֤λ��Ȥ��ѹ����Ǥ���Τϡ��ץ������ΤߤǤ����ץ������ο����񤤤� proctype ����ˤ��������ޤ������Ȥ��С�1 �ĤΥ��������ѿ� state ���ĥץ��������������򲼵��˼����ޤ���

	proctype A()
	{	byte state;

		state = 3
	}

���ξ�硢�ץ���������̾���� A �Ȥʤ�ޤ�����������Τ����� {} �ǰϤߤޤ�����������Τϡ�0�İʾ�Υ��������ѿ������������ӡ�ʸ�Υꥹ�Ȥ���ʤ�ޤ����嵭������ϡ�1 �ĤΥ��������ѿ�������ѿ� state ���� 3 ����������ҤȤĤ�ʸ����ʤ�ޤ���

ʸ�ϡ����ߥ�����ˤ��ʬ�����ޤ��ʥ��ߥ������ʸ�ν�λ����ǤϤ���ޤ��󡣤��Τ��ᡢ�Ǹ��ʸ�Τ������Υ��ߥ�����ϰ�̣������ޤ���ˡ�Promela �� 2 �Ĥΰۤʤ�ʸ��ʬΥ������������� '->' �ȥ��ߥ����� ';'�ˤ�����ޤ���2 �Ĥΰ㤤�Ϥ���ޤ����������ϤȤ��ɤ� 2 �Ĥ�ʸ�ΰ��̴ط���ɽ���Τ˻Ȥ��ޤ������Ȥ��С��ʲ�����Τ褦�˻Ȥ��ޤ���

	byte state = 2;

	proctype A()
	{	(state == 1) -> state = 3
	}

	proctype B()
	{	state = state - 1
	}

������Ǥϡ�2 �ĤΥץ������� A �� B ��������Ƥ��ޤ����ѿ� state �ϥ������Х��ѿ��Ȥ���������졢�� 2 �ˤ����������ޤ����ץ������� A ���������ˤ��ʬ����줿 2 �Ĥ�ʸ����ʤ�ޤ���������Ǥϡ��ץ������� B ���ѿ� state ���ͤ� 1 ���餹�ҤȤĤ�ʸ����ʤ�ޤ�������ʸ�Ͼ�˼¹Բ�ǽ�ʤΤǡ�B ���Υץ������ϥ֥��å��������ʤ���ˤ���ư���λ����������Ǥ��ޤ������� A ���Υץ��������ѿ� state ���ͤ�Ŭ�ڤ��ͤ�Ȥ�ޤǾ��ʸ�ΤȤ����ǥ֥��å�����ޤ���

�ץ������Υ��󥹥���������Process Instantiation��

proctype �ˤ������ϥץ������ο����񤤤��������Τߤǡ��¹ԤϤ��ޤ���Promela ��ǥ�ǤϤϤ��ᡢ������ init �ΤҤȤĤΥץ������Τߤ��¹Ԥ���ޤ������Υץ��������Ϥ��٤Ƥ� Promela ��ǥ���������Ū���������ɬ�פ�����ޤ�*1��Promela ������Ǥ���Ǥ⾮������ǥ�ϡ��ʲ��Τ�ΤǤ���

	init { skip }

skip �ϲ��⤷�ʤ����ߡ���ʸ�Ǥ�����������̣�������ˡ����ν���ץ������ϥ������Х��ѿ������������ץ������Υ��󥹥��󥹤��������뤳�Ȥ��Ǥ��ޤ����嵭�Υ����ƥ��Ѥ� init �ץ�����������ϰʲ��Τ褦�ˤʤ�ޤ���

	init
	{	run A(); run B()
	}

run �ϥץ�������̾�����㤨�С�A�ˤ�����ˤȤ�ñ��黻�ҤǤ���run �ϡ����Υץ����������������Ƥ��ƥ��󥹥��󥹤������Ǥ���Ȥ��Τ߼¹Բ�ǽ�Ǥ������Ȥ��Ф��Ǥˤ�������Υץ����������äƤ��ƿ����ʥ��󥹥��󥹤������Ǥ��ʤ��Ȥ��ϡ��¹��Բ�ǽ�Ȥʤ�ޤ���

run �ϡ���������ץ��������Ф����ܥǡ������Υѥ�᡼�����Ϥ������Ǥ��ޤ������Ȥ��С��ʲ��Τ褦������򵭽Ҥ�������Ǥ��ޤ���

	proctype A(byte state; short foo)
	{
		(state == 1) -> state = foo
	}

	init
	{
		run A(1, 3)
	}

�ǡ�����������ץ���������ѥ�᡼���Ȥ����Ϥ����ϤǤ��ޤ��󡣸�Ǹ���褦�ˡ����ܥǡ������ʳ��˥ѥ�᡼���Ȥ����Ϥ���Τϡ�ͣ���å���������ͥ�ΤߤǤ���

�����ʥץ��������������� run �� init �ץ����������Ǥʤ����٤ƤΥץ������ǻ��Ѳ�ǽ�Ǥ����ץ������ϡ�run �ˤ����������ޤ����ץ������ϡ���λ�����Ȥ��ˡʤ��ʤ�����ץ��������������������ʬ�κǸ�ޤ���ã����ȡ˻Ѥ�ä��ޤ����ץ������ϼ��Ȥ����������ץ���������λ���Ƥ��齪λ���ޤ���

run �ˤ��ץ������� A �� B �Υ��ԡ��򤤤��ĤǤ�������Ǥ��ޤ����������ҤȤİʾ���¹ԥץ��������ҤȤĤΥ������Х��ѿ����ɤ߽񤭤����硢�褯�Τ��������������������ͤޤ����[2] ���㤬����ޤ��ˡ����Ȥ��С��ʲ��Τ褦�� 2 �ĤΥץ��������������Х��ѿ� state ��ͭ���륷���ƥ��ͤ��ޤ��礦��

	byte state = 1;

	proctype A()
	{	byte tmp;
		(state==1) -> tmp = state; tmp = tmp+1; state = tmp
	}

	proctype B()
	{	byte tmp;
		(state==1) -> tmp = state; tmp = tmp-1; state = tmp
	}

	init
	{	run A(); run B()
	}

�⤷ 2 �ĤΤ����ҤȤĤΥץ����������Υץ��������������Ȥ������˴�λ���Ƥ��ޤ��ȡ��⤦�����Υץ������ϤϤ���ξ��ʸ�ΤȤ����DZʱ�˥֥��å�����Ƥ��ޤ��ޤ����⤷ 2 �ĤΥץ�������Ʊ���˾��ʸ���̤�ȴ�����顢2 �ĤȤⴰλ��������Ǥ���Ǥ��礦�����������ΤȤ��� state ���ͤ�ͽ¬�Բ�ǽ�Ǥ���state ���ͤ� 0, 1, 2 �Τ����Τɤ줫�ˤʤ�Ǥ��礦��

��������ˤϤ�������β򤬹ͤ����ޤ����������Х��ѿ���Ȥ�ʤ��Ȥ����褦����ˡ���顢��ͭ�ѿ��Υƥ��Ȥȥ��åȤ��Բ�ʬ�ǹԤ������ݾڤ������̤ʥޥ��������Ѥ�����ˡ�ޤǡ���������Ϻǽ�˸������줿��ΤҤȤĤǤ�������ϥɥ��Ĥο��ؼ� Dekker �ˤ���ΤǤ������Υ��르�ꥺ��ˤ�ꡢ3 �ĤΥ������Х��ѿ���Ȥ������������Ǥ�դ�����ƥ����륻��������ؤο����� 2 �ĤΥץ���������¾Ū�˹Ԥ����Ȥ��Ǥ��ޤ���Promela ��ǥ�κǽ�� 4 �Ԥϡ�C ���쥹������Υޥ�������Ǥ����ǽ�� 2 �ĤΥޥ����� true ����� 1��false ����� 0 ��������Ƥ��ޤ���Ʊ�ͤˡ�Aturn, Bturn ������Ȥ���������Ƥ��ޤ���

	#define true	1
	#define false	0
	#define Aturn	false
	#define Bturn	true

	bool x, y, t;

	proctype A()
	{	x = true;
		t = Bturn;
		(y == false || t == Aturn);
		/* critical section */
		x = false
	}

	proctype B()
	{	y = true;
		t = Aturn;
		(x == false || t == Bturn);
		/* critical section */
		y = false
	}

	init
	{	run A(); run B()
	}

���Υ��르�ꥺ��ϡ������֤��¹Ԥ�������Ǥ���2�ĤΥץ������μ¹ԥ��ԡ��ɤˤϤޤä�����¸���Ƥ��ޤ���

atomic �������󥹡�Atomic Sequences��

Promela �ˤϤ����ƥ��� & ���å����������򤹤��̤μ��ʤ�����ޤ�������ϡ�atomic �Ǥ���������� atomic �ǰϤޤ��ʸ�Υ������󥹤ϡ�¾�Υץ������ˤ�äƥ��󥿡��꡼�֤��줺���Բ�ʬ�˼¹Ԥ���ޤ���atomic �������󥹤���κǽ��ʸ�ʳ��ΤȤ����ǥ֥��å����줿��硢��󥿥��२�顼�Ȥʤ�ޤ�*2�����Τ褦�� atomic �������󥹤�Ȥ����ˤ�ꡢ�����˼������������Х��ѿ� state ���Ф����¹ԥ��������˴ؤ���������ɤ����Ȥ��Ǥ��ޤ���

	byte state = 1;

	proctype A()
	{	atomic {
		  (state==1) -> state = state+1
		}
	}

	proctype B()
	{	atomic {
		  (state==1) -> state = state-1
		}
	}

	init
	{	run A(); run B()
	}

���Υ������Ǥ� state �κǸ���ͤϡ��ɤ���Υץ��������¹Ԥ������ˤ�� 0 �ޤ��� 2 �ˤʤ�ޤ����⤦�����Υץ������ϱʱ�˥֥��å�����ޤ���

atomic �������󥹤ϸ��ڤ����ǥ��ʣ������ڸ�������פ�ƻ��Ǥ���atomic �������󥹤�ʬ�������ƥब�Ȥꤦ�륤�󥿡��꡼�ӥ󥰤����¤��뤳�Ȥ����դ��Ƥ����������㤨�С����������ѿ����Ф������� atomic �������󥹤Ȥ��뤳�Ȥˤ�äơ�ʣ���ʥ�ǥ�򰷤������Ǥ���褦�ˤʤ�ޤ�������ˤ��ʣ�������Ū�˸�������������Ǥ��ޤ���

��å������̿���Message Passing��

��å���������ͥ��ϤҤȤĤΥץ���������¾�Υץ������ؤΥǡ���ž�����ǥ벽����Τ˻��Ѥ���ޤ����ʲ��Ǽ����褦�ˡ�����ͥ�ϥ��������ѿ��Ǥ⥰�����Х��ѿ��Ǥ�����Ǥ��ޤ���

	chan qname = [16] of { short }

�嵭�� short ���Υ�å������� 16 ���ݻ���������Ǥ������ͥ��������Ƥ��ޤ�������ͥ��̾���ϥ���ͥ���̤���¾�Υץ����������ä��ꡢ�ץ������Υ��󥹥����������Υѥ�᡼���Ȥ����Ϥ����ꤹ�뤳�Ȥ��Ǥ��ޤ����⤷���Υ���ͥ�Ǥ���ꤵ����å��������ҤȤİʾ�Υե�����ɤ���ľ�������ϰʲ��Τ褦�ˤʤ�ޤ���

	chan qname = [16] of { byte, int, chan, byte }

���ΤȤ����Υ���ͥ�ϡ����줾�� 2 �Ĥ� 8 bit���͡�1 �Ĥ� 32 bit���͡�����ͥ��̾�����ĥ�å������� 16 ���ݻ����뤳�Ȥ��Ǥ��ޤ���

����ʸ��

	qname!expr

�ϡ��� expr ���ͤ�嵭����Ǻ�ä�����ͥ� qname ���������ޤ�������ͥ�Ρʥ��塼�Ρ������ˤ����ͤ��ɲä��ޤ���

	qname?msg

���ʸ�ϡ�����ͥ����Ƭ�����å���������������ѿ� msg ���������ޤ�������ͥ�� first-in-first-out ��ǥ�å���������Ȥꤷ�ޤ����嵭�Υ������ǤϤҤȤĤ��ͤ�����ͥ���̤��Ƥ��Ȥꤵ��Ƥޤ����⤷��å��������Ȥ� 2 �İʾ���ͤ���Ȥꤷ�������ϡ������Τ褦�˥���ޤǶ��ڤä��ꥹ�Ȥ����ͥ��³�����Ҥ��ޤ���

	qname!expr1,expr2,expr3
	qname?var1,var2,var3

����ͥ����������å��������������Υѥ�᡼����¿���ä��ꡢ���ʤ��ä��ꤷ�����ϥ��顼�Ȥʤ�ޤ���
�ص��Τ��ᡢ��å������κǽ�Υե�����ɤϤ褯��å����������פ�ɽ������˻Ȥ��ޤ��ʤĤޤꡢ������Ȥ������¿���ΤǤ��ˡ����Τ褦�ʾ����̤ν����Ȥ��ơ����������Υѥ�᡼���򡢥�å����������פ�³����̤Ǥ����äƥ�å������ե�����ɤΥꥹ�Ȥ�³���뤳�Ȥ�����ޤ���

	qname!expr1(expr2,expr3)
	qname?var1(var2,var3)

��å��������������ϡ�����ͥ뤬���äѤ��Ǥʤ��Ȥ��¹Բ�ǽ�Ȥʤ�ޤ����ޤ��������ϼ������褦�Ȥ��Ƥ������ͥ뤬���Ǥʤ��Ȥ��¹Բ�ǽ�Ȥʤ�ޤ����ޤ����������Υѥ�᡼���Τ����Ĥ�������Ȥ������Ǥ��ޤ���

	qname?cons1,var2,cons2

���ξ�硢����ǻ��ꤷ�����٤ƤΥ�å������ե�����ɤ��ͤ�����ͥ����Ƭ�Υ�å������Ȱ��פ����硢�������ϼ¹Բ�ǽ�Ȥʤ�ޤ��������֤��ˤʤ�ޤ������¹��Բ�ǽ�Ǥ��ä��Ȥ��Ƥ�ʤˤⰭ�����Ϥ����ޤ��󡣥ץ������Ϥ���ʸ���¹Բ�ǽ�ˤʤ�ޤǥ֥��å�����뤫��¾�μ¹Բ�ǽ��ʸ��¹Ԥ��ޤ���

�����ˤ��ޤޤǾҲ𤷤������Ĥ��ε�����Ȥä���򼨤��ޤ��礦��

	proctype A(chan q1)
	{	chan q2;
		q1?q2;
		q2!123
	}

	proctype B(chan qforb)
	{	int x;
		qforb?x;
		printf("x = %d\n", x)
	}

	init {
		chan qname = [1] of { chan };
		chan qforb = [1] of { int };
		run A(qname);
		run B(qforb);
		qname!qforb
	}

�ץ��Ȥ�����ͤϡ�123 �Ȥʤ�ޤ���

����Ѥߤδؿ� len(qname) �ϥѥ�᡼�����Ϥ���̾�����ĥ���ͥ�˸�����¸����Ƥ����å������ο����֤��ޤ����⤷����ʸ�α��դǤϤʤ�ñ�ˤҤȤĤ�ʸ�Ȥ��ƻȤ�줿��硢����ͥ뤬���ξ��ϼ¹��Բ�ǽ�ˤʤ�������դ��Ƥ����������ʤ��ʤ顢���ξ��� 0 ���֤�������ˤ�ꤽ��ϰ��Ū�˼¹��Բ�ǽ�Ȥʤ뤫��Ǥ����ޤ���

	(qname?var == 0)	/* syntax error */

�ޤ���

	(a > b && qname!123)	/* syntax error */

�Τ褦�ˡ�Promela �ǤϾ��ʸ�������������Ȥ߹�碌�뤳�ȤϤǤ��ޤ���ʤ��Τ褦�ʾ��ʸ�������Ѥʤ��ˤ�ɾ���Ǥ��ʤ��������դ��Ƥ��������ˡ��嵭�Τ褦�ʼ���ʸ������ˡ�? �Τ������� [] ��Ȥ����Ȥ��Ǥ��ޤ���

	qname?[ack,var]

����ʸ�ϡ����ʸ�Ȥ���ɾ������ޤ����⤷�ʲ���ʸ���¹Բ�ǽ���ä����qname ����ͥ����Ƭ�� ack ��å����������ä���ˡ�1 ���֤��ޤ��������Ǥʤ���С�0 ���֤��ޤ���

	qname?ack,var

�ʲ���ʸ�ϡ������Ǥ��뤫�ɤ���ɾ������ޤ������褷�Ƽ������ʤ��������ѤΤʤ�ʸ�Ǥ���

	qname?[ack,var]

�ʲ��Τ褦�� non-atomic �ʥ������󥹤����դ��Ƥ���������

	(len(qname) < MAX) -> qname!msgtype

�ޤ���

	qname?[msgtype] -> qname?msgtype

������ʸ�ϡ�2 ���ܤ�ʸ���ҤȤ��ܤ�ʸ�Τ��Ȥ�ɬ���¹Ԥ����Ȥϸ¤�ޤ���ʣ���Υץ������֤Ƕ�ͭ�������ͥ�˥�������������ϥ졼������ǥ������¸�ߤ��뤫�⤷��ޤ��󡣺ǽ�Υ������Ǥϡ����Υץ�����������ͥ뤬���äѤ��ǤϤʤ��ȷ��ꤷ��ľ���¾�Υץ����������Υ���ͥ�إ�å�������������������Ǥ��ޤ����ޤ���2 ���ܤΥ������ϡ������Υץ���������å�������¸�ߤ��ǧ����ľ��ˡ�¾�Υץ����������Υ�å�������å����뤳�Ȥ��Ǥ��ޤ���

���ǥ��̿���Rendez-Vous Communication��

�����ޤǤϥ�å���������ͥ��𤷤���Ʊ���̿��ˤĤ��Ƹ��Ƥ��ޤ����������� N �����������Ȥ���ȡ��Хåե������� N �Υ���ͥ��ʲ��Τ褦��������Ƥ��ޤ�����

	chan qname = [N] of { byte }

���ΤȤ�������Ū�ˤϰʲ��Τ褦�������ǧ����ޤ���

	chan port = [0] of { byte }

����ϡ�byte ��å������ҤȤĤ���Ȥꤹ����ǥ֥ݡ��Ȥ�������Ƥ��ޤ�������ͥ�Υ������� 0 �Ǥ���Ȥ������Ȥϡ������ݡ����ϥ�å��������ݻ����Ƥ������ϤǤ��ޤ��󡣤��Τ褦�ʥ��ǥ֥ݡ��Ȥ�𤷤ƤΥ�å������Τ�����Ʊ���ˤʤ�ޤ����Ĥ��Τ褦�����ͤ��Ƥߤޤ��礦��

	#define msgtype 33

	chan name = [0] of { byte, byte };

	proctype A()
	{	name!msgtype(124);
		name!msgtype(121)
	}

	proctype B()
	{	byte state;
		name?msgtype(state)
	}

	init
	{	atomic { run A(); run B() }
	}

����ͥ� name �ϥ������Х�ʥ��ǥ֥ݡ��ȤȤ����������Ƥ��ޤ���2 �ĤΥץ������Ϻǽ��ʸ��Ʊ�����Ƽ¹Ԥ��ޤ���msgtype �ˤ��ϥ�ɥ��������ˤ�ꡢ124 �� B �Υ��������ѿ� state ��ž������ޤ���A �� 2 ���ܤ�ʸ�ϼ¹ԤǤ��ޤ��󡢤ʤ��ʤ�ץ����� B �ˤ�����б�����������ʤ�����Ǥ���

�⤷����ͥ� name �� 0 �ǤϤʤ��Хåե����������������Ƥ���ȡ������񤤤ϰۤʤ�ޤ����Хåե������������ʤ��Ȥ� 2 ����С��ץ����� B ���������Ȥ������Ǥ��ä��Ȥ��Ƥ�ץ����� A �ϼ¹Ԥ�λ��������Ǥ����Ǥ��礦���Хåե��������� 1 �ξ��ϡ����Τ褦�ʥ������󥹤Ȥʤ�Ǥ��礦���ץ����� A ���ǽ����������Ԥä��塢2 ���ܤ��������ǥ���ͥ뤬�ե�Τ���֥��å�����ޤ���³���ơ��ץ����� B ���ǽ�Υ�å�������������ޤ������λ����ǥץ����� A �ϺƤӼ¹Բ�ǽ�Ȥʤꡢ�ɤΥץ�������������ʤ�;ʬ�ʥ�å��������������ޤ�����

���ǥ��̿��ϡ�2 �Դ֤ǹԤ��ޤ������ǥ��̿��ˤ��Ʊ�����Ȥ��Τϡ������ץ������ȼ����ץ������� 2 �ĤΥץ����������Ǥ�����Ⱦ�Ǥϥ��ޥե��ι��ۤ��뤿��ˤ��Υ��ǥ��̿������Ѥ�����򸫤ޤ����������������ˡ����Ω�������ʤ����Ĥ������湽¤�ˤĤ��ƾҲ𤷤����Ȼפ��ޤ���

���湽¤��(Control Flow��

����ޤǤˡ�ʸ��Ϣ�롢�ץ��������¹Լ¹ԡ����ȥߥå��������󥹤� 3 �Ĥ����湽¤�򸫤Ƥ��ޤ����������Ǥϡ������ Promela �ǤȤꤢ����٤� 3 �Ĥ����湽¤�ˤĤ��ƾҲ𤷤ޤ�������ȿ����̵��兩���פ� 3 �ĤǤ���

�����Case Selection��

�Ǥ�ñ��ʹ�¤������¤�Ǥ������Ȥ��С�2 �Ĥ��ѿ� a �� b �δط���Ȥä� 2 �ĤΥ��ץ�����񤯻����Ǥ��ޤ���

	if
	:: (a != b) -> option1
	:: (a == b) -> option2
	fi

����¤�� 2 �Ĥμ¹ԥ������󥹤���ʤ�ޤ������줾���Ƭ�ˤϥ����� 2 �Ĥ򤪤��ޤ����ꥹ�Ȥ��椫��¹Ԥ���륷�����󥹤ϤҤȤĤ����Ǥ����ǽ��ʸ���¹Բ�ǽ�ʤ�ΤΤ����ҤȤĤ��¹Ԥ���ޤ����ǽ��ʸ���������ȸƤФ�ޤ���

�嵭����Ǥϡ������ɤ���¾Ū�ˤʤäƤ��ޤ�����ɬ�����⤽���Ǥʤ���Фʤ餤�Ȥ����櫓�ǤϤ���ޤ��󡣤⤷�ҤȤİʾ�Υ����ɤ��¹Բ�ǽ�ʾ�硢�¹Բ�ǽ�ʤ�ΤΤ����ɤΥ������󥹤��¹Ԥ���뤫�������Ū�Ǥ����⤷���٤ƤΥ����ɤ��¹��Բ�ǽ���ä���硢�ץ������Ϥ����ʤ��Ȥ�ҤȤĤΥ����ɤ�����Ǥ���褦�ˤʤ�ޤǥ֥��å�����ޤ��������ɤȤ��ƻ��ѤǤ���ʸ�μ�������¤Ϥ���ޤ��󡣰ʲ��˼����褦�ˡ���å������μ�������񤯻����Ǥ��ޤ���

	#define a 1
	#define b 2

	chan ch = [1] of { byte };

	proctype A()
	{	ch!a
	}

	proctype B()
	{	ch!b
	}

	proctype C()
	{	if
		:: ch?a
		:: ch?b
		fi
	}

	init
	{	atomic { run A(); run B(); run C() }
	}

������Ǥ� 3 �ĤΥץ������ȤҤȤĤΥ���ͥ��������Ƥ��ޤ����ץ����� C ������¤�κǽ�Υ��ץ����ϥ���ͥ�˥�å����� a�ʤ����Ǥ� a �ϥޥ������������Ƥ���褦����� 1�ˤ��ޤޤ��Ȥ��¹Բ�ǽ�ˤʤ�ޤ���2 ���ܤΥ��ץ����ϥ�å����� b��a ��Ʊ�ͤˤ��������ˤ��ޤޤ��Ȥ��¹Բ�ǽ�ˤʤ�ޤ����ץ������μ¹ԥ��ԡ��ɤ˴ؤ����ä˲��⵬�ꤷ�Ƥ��ʤ����ᡢ�ɤ���Υ�å��������ǽ���Ϥ�����ʬ����ޤ���

�ʲ��Υץ��������ѿ� count ����٤��� +1 ���뤫��-1 ���ޤ���

	byte count;

	proctype counter()
	{
		if
		:: count = count + 1
		:: count = count - 1
		fi
	}

ȿ����Repetition��

����¤������Ū��Ĺ�����ȿ����¤������ޤ����嵭����Ǽ������ץ������˼��ä��ơ��ѿ����ͤ򷫤��֤�������˥��åץ����󤵤���ץ����������뤳�Ȥ��Ǥ��ޤ���

	byte count;

	proctype counter()
	{
		do
		:: count = count + 1
		:: count = count - 1
		:: (count == 0) -> break
		od
	}

�¹ԤΤ��ӤˤҤȤĤΥ��ץ�������Ф�ޤ������Υ��ץ�����¹Ԥ������ȡ����ι�¤�򷫤��֤��¹Ԥ��ޤ���ȿ����¤��λ����ˤ��̾� break ʸ����Ѥ��ޤ���������Ǥϡ������ѿ� count ���ͤ� 0 �ΤȤ��˥롼�פ���ȴ��������Ǥ��ޤ���count �� 0 �ΤȤ���ɬ������ break ��¹Ԥ���櫓�ǤϤʤ��Ȥ������Ȥ����դ��Ƥ���������¾�� 2 �ĤΥ��ץ����Ͼ�˼¹Բ�ǽ�ʤΤǡ�count �� 0 �ˤʤä�����Ȥ��ä�ɬ������ break �����櫓�ǤϤʤ��ΤǤ���count �� 0 �ˤʤä��Ȥ���ɬ�� break ����褦�ˤ���ˤϡ��ʲ��Τ褦�˥ץ��������ѹ�����ɬ�פ�����ޤ���

	proctype counter()
	{
		do
		:: (count != 0) ->
			if
			:: count = count + 1
			:: count = count - 1
			fi
		:: (count == 0) -> break
		od
	}

̵��兩���ס�Unconditional Jumps��

�롼�פ���ȴ����⤦��Ĥ���ˡ�ϡ�̵��兩���ס���̾�⤤ goto ʸ������Ѥ�����ˡ�Ǥ����ʲ�����ϡ�0 �ǤϤʤ� 2 �Ĥ����������κ��������򸫤Ĥ���桼����åɤΥ��르�ꥺ������������ΤǤ���

	proctype Euclid(int x, y)
	{
		do
		:: (x >  y) -> x = x - y
		:: (x <  y) -> y = y - x
		:: (x == y) -> goto done
		od;
	done:
		skip
	}

������� goto �Ǥϥ�٥� done �إ����פ��ޤ�����٥��ʸ�����ˤ���ɬ�פ�����ޤ����嵭�Ǥϥץ������κǸ�˥����פ��������ΤǤ������������ä��������Ǥϥ��ߡ�ʸ�� skip �����Ω���ޤ���skip �Ϥ��ĤǤ�¹Բ�ǽ�ʲ�����Ѥ�ڤܤ��ʤ�ʸ�Ǥ����ޤ� goto �Ͼ�˼¹Բ�ǽ�Ǥ���

�ʲ�����Ǥϥ���ͥ� in �����äƤ����å������򤽤��礭���ˤ�ꤽ�줾�� large ����ͥ�� small ����ͥ��ʬ�ۤ���ե��륿��������Ƥ��ޤ����ޥ����ˤ����� N �� 128 �ˡ�size �� 16 ���������Ƥ��ޤ���

	#define N    128
	#define size  16

	chan in    = [size] of { short };
	chan large = [size] of { short };
	chan small = [size] of { short };

	proctype split()
	{	short cargo;

		do
		:: in?cargo ->
			if
			:: (cargo >= N) ->
				large!cargo
			:: (cargo <  N) ->
				small!cargo
			fi
		od
	}

	init
	{	run split()
	}

�ʲ��˼����ץ������� merge �ϡ�2�ĤΥ��ȥ꡼���ƤӤҤȤĤˤޤȤ�ޤ��������������֤Ϥ�ȤΤ�Τϰۤʤ뤳�Ȥˤʤ�Ǥ��礦��

	proctype merge()
	{	short cargo;
	
		do
		::	if
			:: large?cargo
			:: small?cargo
			fi;
			in!cargo
		od
	}

�⤷ init �ץ�������ʲ��Τ褦�ˤ����顢split �� merge �ץ������ϱʱ������³����Ǥ��礦��

	init
	{	in!345; in!12; in!6777;
		in!32;  in!0;
		run split();
		run merge()
	}

�Ǹ����ϡ����ǥ��̿���Ȥäƥ��������ȥ�Υ��ޥե������������ΤǤ���

	#define p	0
	#define v	1
	
	chan sema = [0] of { bit };
	
	proctype dijkstra()
	{	byte count = 1;
	
		do
		:: (count == 1) ->
			sema!p; count = 0
		:: (count == 0) ->
			sema?v; count = 1
		od	
	}
	
	proctype user()
	{	do
		:: sema?p;
		   /*     critical section */
		   sema!v;
		   /* non-critical section */
		od
	}
	
	init
	{	run dijkstra();
		run user();
		run user();
		run user()
	}

���ޥե��ϥ���ƥ����륻�������� 2 �İʾ�Υץ�������Ʊ���ˤ��ʤ����Ȥ��ݾ㤷�Ƥ���ޤ������������ҤȤĤΥץ�����������ƥ����륻������������Ū�˥����������뤳�Ȥ���򤷤Ƥ����櫓�ǤϤ���ޤ���

��³���Υ�ǥ��󥰤ȺƵ���Modeling Procedures and Recursion��

��³���ϡ����Ȥ��Ƶ�Ū�Ǥ⡢�ץ������ˤ�äƥ�ǥ벽��ǽ�Ǥ����֤��ͤϥ������Х��ѿ�������å������ˤ�äƸƤӽФ��ץ��������֤���ޤ����ʲ��Υץ������Ϥ���򼨤�����ΤǤ���

	proctype fact(int n; chan p)
	{	chan child = [1] of { int };
		int result;
	
		if
		:: (n <= 1) -> p!1
		:: (n >= 2) ->
			run fact(n-1, child);
			child?result;
			p!n*result
		fi
	}
	init
	{	chan child = [1] of { int };
		int result;
	
		run fact(7, child);
		child?result;
		printf("result: %d\n", result)
	}

�ץ����� fact(n, p) �ϡ�n �γ����Ƶ�Ū�˷׻������ƥץ����� p �إ�å������ˤ���̤��֤��ޤ���

�����ॢ���ȡ�Timeouts��

����ޤǤ� Promela �Ǥ�����Ѥߤ�ʸ�� 2 �ġ�skip �� break �ˤĤ��ƾҲ𤷤ޤ������⤦�ҤȤĤ�����Ѥߤ�ʸ�� timeout �Ǥ���timeout �ϡ����Υ���ͥ뤫���å��������ԤĤ褦�ʡ��褷�ƿ��ˤϤʤ�ʤ������ԤĤΤ����Ǥ��뤿��ˤĤ���줿�����̤ʾ����ǥ벽������ΤǤ���timeout ������ɤϡ������ƥब�ϥ󥰤������֤����æ�Ф� Promela �ǥ�ǥ벽���뤿��Τ�ΤǤ���timeout ���ϡ�ʬ�������ƥ����¾�Τ��٤Ƥ�ʸ���¹��Բ�ǽ�ˤʤä��Ȥ��˿��ˤʤ�ޤ�������Ū�ʥ����ߥ󥰤��θ�ˤ���Ƥ��ʤ����Ȥ����դ��Ƥ�������������ϸ��ں�Ȥˤ����ƶˤ�ƽ��פʤ��ȤǤ����ޤ��������� timeout ���ɤΤ褦�˼��������٤����ˤĤ��Ƥ��������Ƥ��ޤ��󡣰ʲ��ˡ������ƥब�Ԥ��ͤޤä��Ȥ��ˤϤ��ĤǤ� guard ����ͥ�� reset ��å���������������ץ���������򼨤��ޤ���

	proctype watchdog()
	{
		do
		:: timeout -> guard!reset
		od
	}

ɽ����Assertions��

Promela ��¿��������ɬ�פʽ��פʤ⤦�ҤȤĤθ��칽�����Ǥ� assert ʸ�Ǥ�������ʸ�ϰʲ��η�����Ȥ�ޤ���

	assert(any_boolean_condition)

assert �Ϥ��ĤǤ�¹Բ�ǽ�Ǥ����⤷��郎�������줿�ʤ�С�����ʸ�Ϥʤˤ���Ѥ�ڤܤ��ޤ��󡣤��������⤷��郎��������ʤ��ä��顢����ʸ�ϥ��顼����𤹤�Ǥ��礦��

���٤ʻȤ�����Advanced Usage��

���Υ�ǥ�󥰸���ϸ����̤��ò��������Ĥ�������ħ������ޤ������Τ褦����ħ�ϡ����줫������ˤ������٥�λȤ����䡢Promela �ˤ����� timeout ʸ�ΰ�̣�䡢assert �Τ褦��ʸ�λȤ����˸����ޤ���

��λ���֥�٥��End-State Labels��

���ڸ���Ȥ��� Promela ����Ѥ�����ϡ���ǥ벽���������񤤤ˤĤ��������ü��ɽ�����Ǥ���褦�ˤ��ʤ���Фʤ�ޤ����ä� Promela �ˤ�äƥǥåɥ��å���¸�ߤ�����å�������ϡ����ڥץ������ϡ��桼����˾��Ǥ��ʤ��ǥåɥ��å����̾����λ������ʬ������褦�ˤ��ʤ���Фʤ�ޤ���

Promela �Ǥϡ����󥹥��󥹲����줿���٤ƤΥץ��������������Ƥ���ץ���������ΤκǸ�ޤ���ã�������ġ����٤ƤΥ�å���������ͥ뤬���Ǥ�����֤��̾�ν�λ���֤ȸ��ʤ��ޤ��������������٤ƤΥץ��������ץ���������ΤκǸ�ޤ���ã����褦�˥�ǥ벽�����Ȥϸ¤�ޤ����㤨�С������Ĥ��Υץ������� IDLE ���֤˵�³���뤫�⤷��ޤ��󤷡��ޤ�������ץ������Ͽ�������å������μ�����롼�פ���Ƭ���Ԥ�³���뤫�⤷��ޤ���

�����ǡ����ڥץ�����ब���Τ褦�ʽ�λ���֤ȥǥåɥ��å������Τ˸�ʬ���뤿��ˡ�Promela �ǤϽ�λ���֥�٥��Ȥ������Ǥ��ޤ������Ȥ��С����ҤΥץ������� dijkstra() �˥�٥��ҤȤ��ɲä��ޤ�*3��

	proctype dijkstra()
	{	byte count = 1;
	
	end:	do
		:: (count == 1) ->
			sema!p; count = 0
		:: (count == 0) ->
			sema?v; count = 1
		od	
	}

end ��٥���ɲä��뤳�Ȥˤ�ꡢ�ץ������� dijkstra() ���ץ���������κǸ�γ�̤ޤ���ã���ʤ��Ƥ⡢�롼�פ���Ƭ�ˤ���Х��顼�ȤϤʤ�ޤ��󡣤�����󡢤��Τ褦�ʾ��֤ϥǥåɥ��å����֤ΰ������⤷��ޤ��󤬡��⤷�ǥåɥ��å����ޤ�����Ȥ����顢����Ϥ��Υץ������������ǤϤʤ��Ǥ��礦�ʤ⤷¾�Υץ������������ʽ�λ���֤ˤ��ʤ����ϸ��ڥץ�����ब��𤷤Ƥ����Ǥ��礦�ˡ�

�ҤȤĤθ��ڥ�ǥ�ˤĤ��ҤȤİʾ�ν�λ���֤����뤫�⤷��ޤ��󡣤⤷���Τ褦�ʤȤ��ϡ��ץ�������Υ�٥��̾���Ϥ��٤ƥ�ˡ����ˤ��ʤ���Фʤ�ޤ��󡣤ޤ�����λ���֥�٥��̾���ϡ����ʤ餺 end �� 3 ʸ������Ϥ��ɬ�פ�����ޤ���endde, end0, end_appel �Τ褦�˥�٥��դ����줿���֤ϸ��ڥץ������ˤ��٤������ʽ�λ���֤Ȥ��ư����ޤ���

�ץ����쥹���֥�٥��Progress-State Labels��

��λ���֥�٥��Ʊ���褦�ˡ��桼�����ץ����쥹������٥�������������Ǥ��ޤ������ξ�硢�ץ����쥹���֥�٥�ϥץ��ȥ��뤬��Ÿ���ʤ���Фʤ�ʤ����֤˥ޡ������뤳�Ȥ��Ǥ��ޤ����ץ��ȥ���μ¹���ˤ����ץ����쥹���֥�٥��ҤȤĤ��̲ᤷ�ʤ����٤Ƥ�̵�¥�������ϡ�����Ū�˲��롼�ס�starvation loop�ˤˤʤ����ޤ������Ȥ��� dijkstra ����Ǥϡ����ޥե��ƥ��Ȥ������� "progress" �Ȥ�����٥��Ĥ������ڥץ������ϡ��ץ��ȥ���μ¹����ɬ�����ޥե��ƥ��Ȥ���������ץ����������뤳�Ȥ��ǧ���Ƥ���ޤ���

	proctype dijkstra()
	{	byte count = 1;
	
	end:	do
		:: (count == 1) ->
	progress:	sema!p; count = 0
		:: (count == 0) ->
			sema?v; count = 1
		od	
	}

�⤷�ҤȤİʾ�ξ��֤˥ץ����쥹��٥��Ĥ�����ϡ�progress0, progress_foo �Τ褦�� progress ����Ϥޤ��ˡ�����̾���Υ�٥��Ĥ���ɬ�פ�����ޤ���

-a �ե饰����ꤷ�� Spin ���������������ڥץ������ϥ�󥿥��४�ץ���� -l �򥵥ݡ��Ȥ��ޤ������ڥץ������ϡ��ǥե���ȤǤϤޤ��ǥåɥ��å���õ����Ԥ��ޤ��������Υե饰����ꤷ�����ڥץ������� non-progress �롼�פ�õ����Ԥ��ޤ�������õ���ϥǥåɥ��å���õ��������� 2 �ܤλ��֤ȥ�������̤��פ��ޤ���ɸ��μ�ˡ���Ф��������ʲ��ɤϡ���Ϣ����ʬ���Ϥ���פȤ��Ƥ��ޤ��ˡ�

�����������������Message Type Definitions��

���ޤޤǤϡ��ɤΤ褦���ѿ����������Τ����ޤ���C ��������Υޥ�����ȤäƤɤΤ褦��������������Τ����򸫤Ƥ��ޤ�����Promela �ϥ�å����������פ�����Τ���˰ʲ��Τ褦�������ǧ��Ƥ��ޤ���

	mtype = { ack, nak, err, next, accept }

������ˡ�ϡ����줾�����å������������˼ºݤˤɤ����ä��ͤ���Ѥ��뤫�Ȥ������Ȥ���ݤ��Ƥ������Ǥ�깥�ޤ���������Ǥ��������̾���Ϥ��Τޤ޸��ڥץ���������ǻ��Ѥ�������Ǥ��뤿�ᡢ���顼�����������������Ǥ��ޤ���

����ͥ������ˤ����� mtype ������ɤ���Ѥ�����ˤ�ꡢ�б������å������ե�����ɤ���ͤȤ��ƤǤϤʤ�������Ȥ��ư��������Ǥ��ޤ����㤨�С��ʲ��Τ褦������Ǥ��ޤ���

	chan q = [4] of { mtype, mtype, bit, short };

��ʸ��Pseudo Statements��

�����ޤǤϡ�Promela ���������뤹�٤Ƥδ���ʸ����������������������assert��timeout��goto��break��skip�ˤ򸫤Ƥ��ޤ����������ơ�ʸ�Ǥ���ޤ��� chan, len, run �Ȥ��ä����ʸ������ʸ�ǻ��Ѥ�������Ǥ���ñ��黻�ҤˤĤ��Ƥ⸫�Ƥ��ޤ�����

skip ʸ�ϡ��ºݤˤϤޤä������Ѥ�ڤܤ��ʤ�����ʸ���׵���������Τ˥ե��륿������̤���ʸ�Ȥ��ƾҲ𤷤ޤ�����skip �Ϸ���Ū�ˤϸ���ΰ����ǤϤʤ��ΤǤ�����ñ�� ��� (1) �Ƚ񤤤�ñ��ʾ��ʸ��Ʊ�����̤���Ʊ����Ǥ��ꡢ��ʸ�Ǥ���Ʊ���褦�ʵ�ʸ�ˡ�(0) �������� block �� hang��assert(0) �������� halt ���ͤ����ޤ��ʼºݤˤϤ������������Ƥ��ޤ���ˡ�else �Ϥ⤦�ҤȤĤε�ʸ�Ǥ�������������ȿ������ǺǸ�Υ��ץ���󥷡����󥹤�ʸ�Ȥ��ƻ��Ѥ�������Ǥ��ޤ���

	if
	:: a > b -> ...
	:: else -> ...
	fi

else ��Ʊ����������¾�Τ��٤ƤΥ��ץ���󤬼¹��Բ�ǽ�ʤȤ��ˤ����¹Բ�ǽ�ˤʤ�ޤ���

���Example��

Promela �ǥ�ǥ벽����ñ��ʡʷ�٤Τ���˥ץ��ȥ������򼨤��ޤ���

	mtype = { ack, nak, err, next, accept };

	proctype transfer(chan in,out,chin,chout)
	{	byte o, i;
	
		in?next(o);
	
		do
		:: chin?nak(i) ->
				out!accept(i);
				chout!ack(o)
	
		:: chin?ack(i) ->
				out!accept(i);
				in?next(o);
				chout!ack(o)
	
		:: chin?err(i) ->
				chout!nak(o)
		od
	}

	init
	{	chan AtoB = [1] of { mtype, byte };
		chan BtoA = [1] of { mtype, byte };
	
		chan Ain  = [2] of { mtype, byte };
		chan Bin  = [2] of { mtype, byte };
	
		chan Aout = [2] of { mtype, byte };
		chan Bout = [2] of { mtype, byte };
	
		atomic {
		  run transfer(Ain,Aout, AtoB,BtoA);
		  run transfer(Bin,Bout, BtoA,AtoB)
		};
	
		AtoB!err(0)
	}

����ͥ� Ain �� Bin �ϡ������Ǥ�������Ƥ��ʤ��Хå������ɥץ������ʤ���ž�������ƥ�Υ桼���ץ������ˤˤ�äơ���å����������� next ��Ǥ�դ��͡�ASCII��ʸ�������ɡˤΥȡ������å������������ޤ���Ʊ�ͤˡ��桼���ץ������ϡ�����ͥ� Aout, Bout ����ǡ����������������Ǥ��ޤ�������ͥ�ȥץ������ϡ����ȥߥå��˽�������졢���ߡ��� err ��å������ˤ�ꥹ�����Ȥ��ޤ���

Spin��Spin����Spin.html�⸫�Ƥ���������

Promela �ǵ��Ҥ��������ƥ�Υ�ǥ뤬Ϳ����줿�Ȥ���Spin �ϥ����ƥ�Υ����ॷ�ߥ�졼�����򤷤��ꡢ�����ƥ�ξ��ֶ��֤����᤯õ������ C ����θ��ڥץ����������������ꤹ�뤳�Ȥ��Ǥ��ޤ������θ��ڥץ������ϡ����Ȥ��С��ץ��ȥ����¹��桢�桼�������Ҥ��������ƥ�����Ѿ����ȿ���Ƥ��ʤ����������å����ޤ���

���⥪�ץ�������ꤷ�ʤ��� Spin ��ư�������ϡ������ॷ�ߥ�졼������Ԥ��ޤ������ץ���� -n N ����ꤷ�����ϡ������ॷ�ߥ�졼�����Τ���μ������ N �����ꤷ�ޤ���

���ץ���� pglrs �ϡ��桼�������ߥ�졼�����ˤĤ��ƽ��Ϥ���������Υ�٥�����ꤹ��Τ˻��Ѥ��ޤ������ϤΤ��٤ƤιԤϡ��̾��ǥ�Υ������ι��ֹ�ؤλ��Ȥ�ޤߤޤ���

-p �ϡ����٤ƤΥ��ƥåפ��Ф��� Promela �ץ������ξ����Ѳ���ɽ�����ޤ���

-g �ϡ����٤ƤΥ��ƥåפ��Ф��Ƥ��ΤȤ��Υ������Х��ѿ����ͤ�ɽ�����ޤ���

-l �ϡ����������ѿ����ĥץ������������Ѳ��������ȤΥ��������ѿ����ͤ�ɽ�����ޤ���-p ���ץ������Ȥ߹�碌�ƻȤ��Ȥ����Ǥ��礦��

-r �Ϥ��٤ƤΥ�å������������٥�Ȥ�ɽ�����ޤ�������ϼ��������ץ�������̾�����ֹ桢�������ι��ֹ桢��å������Υѥ�᡼���ֹ�ʥѥ�᡼�����Ȥ� 1 �Ԥˤʤ�ޤ��ˡ���å����������פȥ�å���������ͥ��̾�����ֹ��ɽ�����ޤ���

-s �Ϥ��٤ƤΥ�å������������٥�Ȥ�ɽ�����ޤ���

Spin �ǤϤ���� 3 �ĤΥ��ץ�����-a��-m��-t�ˤ���Ѥ�������Ǥ��ޤ���

-a �ϥץ��ȥ�����ò��������ڥץ��������������ޤ������ν��Ϥ� pan.[cbhmt] ��̾�դ����뤤���Ĥ��� C ����Υե�����˽񤭽Ф���ޤ����������줿�ե�����򥳥�ѥ��뤹����ˤ��¹Բ�ǽ�ʸ��ڴ郎��������ޤ������ֶ��֤򤯤ޤʤ�õ��������ϡ�ñ�˼��Τ褦�˥���ѥ��뤹������Ǥ����Ǥ��礦��

	$ gcc -o pan pan.c

�礭�ʥ����ƥ�ξ��ϡ�����ԥ塼���Υ����Ȥ��Ԥ������⤷��ޤ��󡣤��Τ褦���礭�ʥ����ƥ�θ��ڤ򤹤���ϡ�������ΨŪ�˻Ȥ��ӥåȾ��ֶ���ˡ��Ȥ����ˤ�긡�ڤ���ǽ�ˤʤ뤫�⤷��ޤ��󡣥ӥåȾ��ֶ���ˡ����Ѥ���Ȥ��ϰʲ��Τ褦�˥���ѥ��뤷�ޤ���

	$ gcc -DBITSTATE -o pan pan.c

���Τ褦��õ���Υ��Х졼���ϡ��ϥå��������ʾܺ٤ϸ�ҡˤˤ��ޤ����������줿�¹Բ�ǽ�ʸ��ڥץ�����༫�Ȥˤ⥪�ץ�������ꤹ������Ǥ��ޤ������ڥץ������˻���Ǥ��륪�ץ����ϡ��嵭�Τ褦�˥���ѥ��뤷������ "./pan -?" �ˤ���ǧ�Ǥ��ޤ��ʸ��ڥץ������˻���Ǥ��륪�ץ����ˤĤ��Ƥϡ���Ҥ��ָ��ڥץ���������Ѥ�������������ޤ��ˡ�

-m �ϡ���å����������Υǥե���Ȥο����񤤤��ѹ�����Τ˻��Ѥ��ޤ����̾�ϡ��������ϥ������åȤȤʤ����ͥ뤬���äѤ��Ǥʤ��Ȥ������¹Բ�ǽ�ˤʤ�ޤ�������ϰ��ۤΤ�����Ʊ���������������������ޤ���������Ϥ��ĤǤ�˾�ޤ���ΤǤϤ���ޤ���-m ���ץ�������ꤹ����ˤ���������Ͼ�˼¹Բ�ǽ�ˤʤ�ޤ������äѤ��ˤʤäƤ������ͥ������������å������ϼ����ޤ������Υ��ץ����� -a ���ץ������Ȥ߹�碌�Ƹ��ڥץ������������������ϡ���������븡�ڥץ������ο����񤤤�Ʊ�ͤ˰ۤʤ�ޤ������ڤ���ݤˤϡ���å�����������������θ�������ɬ�פ�����Ǥ��礦��

-t �ϡ�����ɽ���ѤΥ��ץ����Ǥ������ڥץ�����ब assert ���Ф����ȿ��ǥåɥ��å���˾�ޤʤ���å������μ����򸫤Ĥ�����硢���ڥץ������� pan.trail �Ȥ���̾�Υե�����˥��顼�ε��פ�񤭽Ф��ޤ���Spin �� -t ���ץ�������ꤹ����ˤ�ꤽ�ξܺ٤򸫤�����Ǥ��ޤ���¾�Υ��ץ�����pglrs�ˤ��Ȥ߹�碌����ˤ�ꥨ�顼�������󥹤��Ф��뤤�������ʻ������ñ�˼�����������Ǥ���Ǥ��礦��

�����ǾҲ𤷤ʤ��ä� Spin ��¾�Υ��ץ����ˤĤ��ƤϾ�ά���ޤ����ܤ����ϡ�[5] �򸫤Ƥ����������ޤ��ҥ�ȤȤ��ơ����Υޥ˥奢��κǸ�ˤ��� "����˿������겼����" �⸫�Ƥ���������

���ߥ�졼����The Simulator��

�ʲ��˼����ץ��ȥ�������ͤ��Ƥߤޤ��礦�������Ǥϡ��ʲ��Υ�ǥ�� lynch �Ȥ����ե��������¸�����Ȥ��ޤ���

   1  #define MIN	9
   2  #define MAX	12
   3  #define FILL	99
   4  
   5  mtype = { ack, nak, err }
   6  
   7  proctype transfer(chan chin, chout)
   8  {	byte o, i, last_i=MIN;
   9  
  10  	o = MIN+1;
  11  	do
  12  	:: chin?nak(i) ->
  13  		assert(i == last_i+1);
  14  		chout!ack(o)
  15  	:: chin?ack(i) ->
  16  		if
  17  		:: (o <  MAX) -> o = o+1
  18  		:: (o >= MAX) -> o = FILL
  19  		fi;
  20  		chout!ack(o)
  21  	:: chin?err(i) ->
  22  		chout!nak(o)
  23  	od
  24  }
  25  
  26  proctype channel(chan in, out)
  27  {	byte md, mt;
  28  	do
  29  	:: in?mt,md ->
  30  		if
  31  		:: out!mt,md
  32  		:: out!err,0
  33  		fi
  34  	od
  35  }
  36  
  37  init
  38  {	chan AtoB = [1] of { mtype, byte };
  39  	chan BtoC = [1] of { mtype, byte };
  40  	chan CtoA = [1] of { mtype, byte };
  41  	atomic {
  42  		run transfer(AtoB, BtoC);
  43  		run channel(BtoC, CtoA);
  44  		run transfer(CtoA, AtoB)
  45  	};
  46  	AtoB!err,0;	/* start */
  47  	0		/* hang */
  48  }

���Υץ��ȥ���ϥ�å����������� ack��nak��err ����Ѥ��ޤ���err �ϡ�2 �Ĥ�ž���ץ������֤Υ���ͥ��̿��ˤ������å������Τ椬�ߤ��ǥ벽����Τ˻��Ѥ��Ƥ��ޤ�������ͥ�ο����񤤤ϥ���ͥ�ץ������ˤ���ǥ벽���Ƥ��ޤ����ޤ�ž���ץ������� 2 �ĤΥ��������ѿ��֤����Ѿ��ʾ嵭�Τ�ΤϤ虜�ȴְ�äƤ��ޤ��ˤ� assert ��Ȥä�ɽ�����Ƥ��ޤ���

���⥪�ץ�������ꤷ�ʤ��� Spin �����餻��ȡ������ॷ�ߥ�졼������Ԥ����¹Ԥ�������ñ�˽��Ϥ��뤫���¹�����̤ä� printf ʸ����Ϥ��ޤ������ξ��ϡ��ʲ��Τ褦�ʽ��Ϥˤʤ�ޤ���

	$ spin lynch	# no options, not recommended
	spin: "lynch" line 13: assertion violated
	#processes: 4
	proc  3 (transfer)	line 11 (state 15)
	proc  2 (channel)	line 28 (state 6)
	proc  1 (transfer)	line 13 (state 3)
	proc  0 (:init:)	line 48 (state 6)
	4 processes created
	$ 

�嵭�Υ�ǥ�ˤ� printf �Ϥʤ��Τ� printf ���Ф�����ϤϤ���ޤ��󤬡��ץ������� assert �˰�ȿ�������ᡢ���Τ��Ȥ����Ϥ���Ƥ��ޤ���������Τꤿ�����ϡ���ꤿ������ʤ��Ȥ��С����٤Ƥμ������٥�ȡ˽��Ϥ���褦�����餻�����Ǥ��ޤ������η�̤򲼤ο� 1 �˼����ޤ������ϤˤĤ��ƤϤۤȤ����������ޤǤ�ʤ��Ǥ��礦��

�嵭�Υ��ߥ�졼�����Ǥϲ��ٹԤäƤ�Ʊ�� assert ��ȿ�򸡽Ф��ޤ������ߥ�졼�����ϥ�����������Ū����򤷤Ƥ���Τǡ��Ĥͤˤ��Υ������ΰ�ȿ�򸫤Ĥ���ɬ�פϤ���ޤ��󡣺Ƹ���ǽ�ʼ¹ԥ������󥹤���������ϡ�-n N ���ץ�����Ȥ��ޤ����㤨�С�

	$ spin -r -n100 lynch

�Ȥ���ȡ������ॸ���ͥ졼���μ������ 100 ����Ѥ������Ʊ�����Ϥ�����������ݾڤ��ޤ���

�̤Υ��ץ�������ꤹ����ˤ�ꡢ���ߥ�졼�����μ¹Ԥˤ����Ϥ�¿���Ф������Ǥ��ޤ��������Ϥ����ƥ����ȤϤ�����������̤ˤʤ�ޤ���������Ф����ñ�ʲ�� grep ��Ȥäƽ��Ϥ�ե��륿��󥰤�����Ǥ������Ȥ��С��嵭����ˤ����ƥ���ͥ�ץ������ο����񤤤�����̣�ʤ��ä��Ȥ��Ƥ顢�ʲ��Τ褦�ˤ��ޤ���

	$ spin -n100 -r lynch | grep "proc  2"

��������ȡ��� 1 �Τ褦�ʷ�̤ˤʤ�ޤ���

	$ spin -r lynch
	proc  1 (transfer) line  21, Recv err,0  <- queue 1 (chin)
	proc  2 (channel)  line  29, Recv nak,10 <- queue 2 (in)
	proc  3 (transfer) line  12, Recv nak,10 <- queue 3 (chin)
	proc  1 (transfer) line  15, Recv ack,10 <- queue 1 (chin)
	...
	proc  1 (transfer) line  15, Recv ack,12 <- queue 1 (chin)
	proc  2 (channel)  line  29, Recv ack,99 <- queue 2 (in)
	proc  3 (transfer) line  15, Recv ack,99 <- queue 3 (chin)
	proc  1 (transfer) line  15, Recv ack,99 <- queue 1 (chin)
	proc  2 (channel)  line  29, Recv ack,99 <- queue 2 (in)
	proc  3 (transfer) line  21, Recv err,0  <- queue 3 (chin)
	proc  1 (transfer) line  12, Recv nak,99 <- queue 1 (chin)
	spin: "lynch" line 13: assertion violated
	#processes: 4
	proc  3 (transfer) line 11 (state 15)
	proc  2 (channel)  line 28 (state 6)
	proc  1 (transfer) line 13 (state 3)
	proc  0 (:init:)   line 48 (state 6)
	4 processes created
	$ spin -n100 -r lynch | grep "proc  2"
	proc  2 (channel) line 29, Recv nak,10 <- queue 2 (in)
	proc  2 (channel) line 29, Recv ack,11 <- queue 2 (in)
	proc  2 (channel) line 29, Recv ack,12 <- queue 2 (in)
	proc  2 (channel) line 28 (state 6)

	�� 1. ���ߥ�졼�����ν���

�ʲ��Τ褦�ʷ�̤�����ˤϡ�-c ���ץ����ʥС������3.0�Ǥο���ǽ�ˤ�Ȥ��ޤ���

	$ spin -c lynch
	proc 0 = :init:
	proc 1 = transfer
	proc 2 = channel
	proc 3 = transfer
	q\p   0   1   2   3
	  1   AtoB!err,0
	  1   .   chin?err,0
	  2   .   chout!nak,10
	  2   .   .   in?nak,10
	  3   .   .   out!err,0
	  3   .   .   .   chin?err,0
	  1   .   .   .   chout!nak,10
	  1   .   chin?nak,10
	  2   .   chout!ack,10
	  2   .   .   in?ack,10
	  3   .   .   out!ack,10
	  3   .   .   .   chin?ack,10
	  1   .   .   .   chout!ack,11
	  1   .   chin?ack,11
	  2   .   chout!ack,11
	  2   .   .   in?ack,11
	  3   .   .   out!ack,11
	  3   .   .   .   chin?ack,11
	  1   .   .   .   chout!ack,12
	  1   .   chin?ack,12
	  2   .   chout!ack,12
	  2   .   .   in?ack,12
	  3   .   .   out!ack,12
	  3   .   .   .   chin?ack,12
	  1   .   .   .   chout!ack,99
	  1   .   chin?ack,99
	  2   .   chout!ack,99
	  2   .   .   in?ack,99
	  3   .   .   out!err,0
	  3   .   .   .   chin?err,0
	  1   .   .   .   chout!nak,99
	  1   .   chin?nak,99
	spin: line  13 "lynch", Error: assertion violated
	-------------
	final state:
	-------------
	#processes: 4
	 79:    proc  3 (transfer) line  11 "lynch" (state 15)
	 79:    proc  2 (channel) line  28 "lynch" (state 6)
	 79:    proc  1 (transfer) line  13 "lynch" (state 3)
	 79:    proc  0 (:init:) line  47 "lynch" (state 6)
	4 processes created

�ǽ���󤬥���ͥ�� id �ֹ桢�ǽ�ιԤ��ץ����� id �ֹ�ǡ��ƹԤϤɤΥץ���������å�������ž����Ԥä�������Ϥ��Ƥ��ޤ���

���ڥץ�������The Analyzer�ˡ�Pan.html �� Roadmap.html �⸫�Ƥ���������

���ߥ�졼�����Ͽ������߷פ�����̤ˤĤ��Ƥ��äȥǥХå�����ˤ����Ω���ޤ��������Υ����ƥब�����˥��顼��ޤ�Ǥ��ʤ����ɤ��������������ϤǤ��ޤ���Spin �Ǥ� -a �� -t ���ץ�����Ȥ����ˤ�ꡢ���Ȥ������礭�ʥ�ǥ�Ǥ��ä��Ȥ��Ƥ⸡�ڤ�������Ǥ��ޤ���

�ץ��ȥ����ǥ���Ф�����ֶ���õ���ץ������ϰʲ��� 1 ���ܤΤ褦�ˤ��ƺ���� 5 �ĥե����뤫��ʤ�ޤ���

	$ spin -a lynch
	$ wc pan.[bchmt]
	     99     285    1893 pan.b
	   3158   10208   70337 pan.c
	    356    1238    7786 pan.h
	    216     903    6045 pan.m
	    575    2099   14017 pan.t
	   4404   14733  100078 total

pan.c �ϥץ��ȥ���θ��ڤ�Ԥ� C ����Υ����ɤΤۤȤ�ɤ�ޤߤޤ���pan.t �ϥץ��ȥ��������ե����򥨥󥳡��ɤ������ܥޥȥꥯ����ޤߤޤ���pan.b �� pan.m �Ͻ����������ܤȵ����������ܤ� C �Υ����ɡ�pan.h �ϥإå��ե�����Ǥ��������Ϥ����Ĥ�����ˡ�ǥ���ѥ��뤹������Ǥ��ޤ��ʤ��Ȥ��С������ֶ���õ������Ȥ����ӥåȾ��ֶ��֤���Ѥ���Ȥ��ˡ�

��õ����Exhaustive Search��

�����ƥ�ξ��ֶ��֤������褽100,000�ۤɤޤǤʤ�С���äȤ��ɤ���ˡ�ϡ��ǥե���ȤΤޤޥץ������򥳥�ѥ��뤹�뤳�ȤǤ���

	$ gcc -o pan pan.c

����ѥ���ˤ�äƤǤ����¹ԥץ������ pan ��¹Ԥ�����ˤ�긡�ڤ�������Ǥ��ޤ������ξ��θ��ڤ���õ����Ԥ��ޤ����Ĥޤꡢ��ǽ�ʤ��٤ƤΥ��٥�ȥ������󥹤�ƥ��Ȥ��ޤ����������assert ��ȿ������Ф���򸫤Ĥ��Ф��ޤ���

	$ ./pan
	assertion violated (i == last_i + 1))
	pan: aborted
	pan: wrote pan.trail
	search interrupted
	vector 64 byte, depth reached 56
	      61 states, stored
	       5 states, linked
	       1 states, matched
	hash conflicts: 0 (resolved)
	(size 2^18 states, stack frames: 0/5)

(��꿷�����С������ν��Ϸ����ϡ�Ʊ�������ޤ�Ǥ��ޤ�������ä���������Ƥ��ޤ���)

���Ϥκǽ�� 1 ���ܤϡ�assert ��ȿ�����ä�������𤷡����Ѿ�郎��������ʤ��ä��ǽ��ȿ��򶵤��Ƥ���ޤ������ΰ�ȿ�� 61 ���֤��������줿���ȯ������Ƥ��ޤ����ϥå��� "conflicts" �ϡ����ֶ��֤򥢥��������Ƥ���֤ˤ������ϥå���ξ��Ͳ���򼨤��Ƥ��ޤ�����õ���⡼�ɤǤϡ����٤Ƥξ��֤ϥꥹ�ȡ�linked list�ˤ˳�Ǽ���ơ����٤Ƥξ��ͤ��褷�Ƥ��ޤ������ξ��ˤ�����Ǥ�ؿ���������ʬ�ϡ�3 ���ܤǤ��礦������ϡ����ߥ�졼���ˤ�äƺƸ���ǽ�ʥ��顼�������󥹤� trail �ե�����˺��줿���Ȥ򼨤��Ƥ��ޤ��������ǰʲ��Τ褦�ˤ���ȡ�

	$ spin -t -r lynch | grep "proc  2"

���顼�θ������ʤˤǤ��ä������ꤹ����Ǥ���Ǥ��礦��assert ��Ŭ�ڤǤ���С����ڥץ������Ϥ��ΰ�ȿ�򸫤Ĥ��Ƥ���ޤ����⤷���Τ褦�ʰ�ȿ����𤵤�ʤ��ä����ϡ��ְ㤤�ʤ� assert ��ȿ���Ȥ��褦�ʼ¹ԥ������󥹤��ʤ��ä��Ȥ������ȤǤ��礦��

���ץ�����Options��

���ڥץ������Ϥ����Ĥ��Υ��ץ���󤬻���Ǥ���褦����������ޤ����ɤΤ褦�ʥ��ץ���󤬤��뤫�ϡ��ʲ��Τ褦�ˤ���ȥ����å��Ǥ��ޤ���

	$ ./pan --
	-cN stop at Nth error (default=1)
	-l  find non-progress cycles	# when compiled with -DNP
	-a  find acceptance cycles	# when not compiled with -DNP
	-mN max depth N (default=10k)
	-wN hash table of 2^N entries (default=18)
	 ...etc.

�ǽ�� -c ���ץ����ΰ����� 0 �����ꤹ��ȡ����ڥץ������ϥ��顼�򸫤Ĥ��Ƥ���ֶ���õ����³���ޤ������顼�����Ĥ���ʤ��ä����� -c0 ���ץ���󤬻��ꤵ�줿���ϡ����θ��ڤ���λ����ȡ��¹ԤǤ��ʤ��ä�����ã�Ǥ��ʤ��ä��˥����ɤ˴ؤ����׻ݤ򼨤��ޤ������ξ��ν��Ϥϰʲ��Τ褦�ˤʤ�ޤ���

	$ ./pan -c0
	assertion violated (i == (last_i + 1))
	
	vector 64 byte, depth reached 60, errors: 5
	     165 states, stored
	       5 states, linked
	      26 states, matched
	hash conflicts: 1 (resolved)
	(size 2^18 states, stack frames: 0/6)
	
	unreached code :init: (proc 0):
		reached all 9 states
	unreached code channel (proc 1):
		 line 35 (state 9),
		reached: 8 of 9 states
	unreached code transfer (proc 2):
		 line 24 (state 18),
		reached: 17 of 18 states

�嵭�ϡ�5 �Ĥ� assert ��ȿ�����ä����Ȥ� 165 �Υ�ˡ����ʥ����ƥ�ξ��֤����줿���򼨤��Ƥ��ޤ������֤˴ؤ��Ƥϡ��ƾ��֤��٥����������� 64 byte �ǡ��۴Ĥ��ʤ���Ĺ�Υ������󥹤� 60 �Ǥ��뤳�Ȥ򼨤��Ƥ��ޤ�������ͥ�ץ�������ž���ץ������Τɤ���ˤ���ã���Ƥ��ʤ����֤��ҤȤĤ��뤳�Ȥ⼨���Ƥ��ޤ�����ã���Ƥ��ʤ����֤ϡ����줾��Υץ������� do �롼�פ�ľ��Ǥ����ɤ���Υ롼�פ⽪λ���ʤ����Ȥ�տޤ��ƺ���Ƥ��뤳�Ȥ����դ��Ƥ���������

-l ���ץ�������ꤹ��ȡ����ڥץ������ϥǥåɥ��å��� assert ��ȿ��� non-progress �롼�פ�õ���ޤ������Υ��ץ����ˤĤ��Ƥ� "�����٤ʻȤ���" ���������ޤ���

���ڥץ������Ϥ���� 2 �ĤΥ��ץ����򥵥ݡ��Ȥ��Ƥ��ޤ����ǥե���ȤǤ�õ���ο����� 10,000 ���ƥåפ����¤���Ƥ��ޤ����⤷õ��������õ�������ˤޤ�ã�������ϡ�õ�����Ǥ��ڤ�뤿�ḡ�ڤ���ʬŪ�ˤʤ�ޤ����μ¤���õ����Ԥ��������ϡ�"depth reached" ������õ����������Ǥ�������ǧ�����⤷�����Ǥʤ��ä����� -m ���ץ�������ꤷ�Ƹ��ڤ򷫤��֤�ɬ�פ�����ޤ���

-m ���ץ����ϡ������������Ū��õ�����Ǥ��ڤ�Τˤ���ѤǤ��ޤ������Ȥ��С�assert ���ȿ����¹ԥ������󥹤Τ�����û�Τ�Τ�õ�������Ȥ��˻Ȥ��ޤ������Τ褦��õ�����Ǥ��ڤ���ϡ�����õ����������Ǥβ�ǽ�ʤ��٤Ƥΰ�ȿ�򸡽Ф�������ݾڤ��ޤ���

�Ǹ�Υ��ץ����� -w N �Ǥ�������������ֶ��֤θ��ڤΥ������פǤϤʤ����¹Ի��֤˱ƶ���ڤܤ��ޤ���"hash table width" ���̾︡�ڥץ�����ब�������륷���ƥ�Υ�ˡ����ʾ��ֿ���ͽ���ͤ��п������������Ǥ���С��礭�����ꤷ�ʤ���Фʤ�ޤ���ʤ⤷����򾮤������ꤹ��ȡ��ϥå���ξ��ͤ����ä���õ���˻��֤�����褦�ˤʤ�Ǥ��礦�ˡ����Υǥե������ 18 �Ǥ� 262,144 ���֤򰷤����Ȥ��Ǥ��������ֶ���õ�����ڤǤϤ��Υǥե�����ͤΤޤޤǽ�ʬ�Ȥʤ�褦�ˤ��٤��Ǥ���

�ӥåȾ��ֶ��ָ��ڡ�Bit State Space Analyses��

�����ֶ���õ���Ǹ��ڤ���Ȥ���ɬ�פȤʤ�����̤ϴ�ñ�˷׻���������Ǥ��ޤ�[4]���⤷���嵭�Υץ��ȥ������Τ褦�ˡ�1 ���֤򥨥󥳡��ɤ���Τ� 64 byte ɬ�פǡ�õ���˻��ѤǤ��륷���ƥ�Υ����̤� 2MB ���Ȥ���ȡ�32,768 ���ֳ�Ǽ��������Ǥ��ޤ����⤷�����ƥ�ξ��ֶ��֤������ã��ǽ�ʾ��ֿ�������ʾ�ˤʤä���硢���ڤϼ��ԤȤʤ�ޤ������ޤΤȤ�����Spin �Ϥ��Υȥ�åפ��򤱤�����Ǥ���ͣ������ڥ����ƥ�Ǥ���¾�μ�ư���ڥ����ƥ�ϡʤ��줬���פȤ��Ƥ����������˴ط��ʤ��ˡ������Ȥ��̤����ȥ桼������Ω���������֤����ʤ����ڤ���Ƥ��ޤ��ޤ���

����θ�����ˡ�Ǥϡ���������¤�ã������硢���Υ��Х졼���ϵ޷�˲����äƤ��ޤ��ޤ������Ȥ��С���Ǽ�Ǥ�����ֿ���2�ܤξ��ֿ����ľ��ֶ��֤򸡾ڤ���Ȥ�������õ����ͭ���ʥ��Х졼���Ϥ��ä��� 50% �Ǥ���Spin �ǤϤ��Τ褦�ʥ������Ǥ�ӥåȾ��ֶ���ˡ[4]��Ȥ����ˤ�꽽ʬ���ɤ���̤������ޤ����ӥåȾ��ֶ��֤�Ȥ��ˤϰʲ��Τ褦�˸��ڥץ������򥳥�ѥ��뤷�ޤ���

	$ gcc -DBITSTATE -o pan pan.c

���Τ褦�˥���ѥ��뤵�줿���ڥץ������Ǥ�������Ʊ���褦�� assert ��ȿ�򸫤Ĥ��Ф������Ǥ��ޤ���

	$ ./pan
	assertion violated (i == ((last_i + 1))
	pan: aborted
	pan: wrote pan.trail
	search interrupted
	vector 64 byte, depth reached 56
	      61 states, stored
	       5 states, linked
	       1 states, matched
	hash factor: 67650.064516
	(size 2^22 states, stack frames: 0/5)
	$ 

�ºݡ������٤��礭��������򾮤������뤿��ˤ�����ˡ��Ȥä����ϡ������ֶ���õ������٤Ƥ�ۤȤ�ɰ㤤�Ϥ���ޤ���ʥӥåȾ��ֶ���ˡ������¿��®������������̤����ʤ˲��������Ƥ��뤳�Ȥ�Τ����ƤϤǤ����ˡ��������礭������򰷤ä��Ȥ��ˤϡ����㤤��ɽ��ޤ������ϤκǸ�� 2 �Ԥˡ����Х졼���θ��Ѥ�꤬�Ф�Τ��礭�ʥ�ǥ�򸡾ڤ���Ȥ��ˤ����Ω�ĤǤ��礦���ӥåȾ��ֶ��֤�Ŭ���Ǥ�����֤κ�����ϡ��Ǹ�ιԤ˽񤤤Ƥ���ޤ��ʤ����Ǥϡ�2 22 byte �ޤ��� 3200 ���ӥåȡʾ��֡ˡˡ����ξ�ιԤ��ϥå��������򼨤��Ƥ��ޤ�������ϼºݤξ��ֿ��dz�ä����֤κ�����ˤ����褽�������Ǥ����礭�ʥϥå������ǡ�100 �ʾ�ˤϿ������ι⤤���򼨤������Υ��Х졼���� 99% �� 100% �Ǥ����ϥå������Ǥ� 1 �˶�Ť��ȡ����Х졼���� 0% �˶�Ť��ޤ���

����θ��ڥ����ƥबõ���Ǥ��ʤ��ä����⤷���ϡ��㤤���Х졼���ȤʤäƤ����������ˤ�������ʬŪ�ʥ��Х졼����¸����Ƥ���Ȥ������˽�ʬ�����դ��Ƥ��������������� Spin ��������������������μ�ư���ڥ����ƥ��꿮�������㤤�Ȥ������Ȥ�����ޤ�����

�ӥåȾ��ָ��ڤ���ɸ�ͤϡ��ӥåȾ��ֶ��֤Υ���κ�������̤򥢥������Ȥ��뤳�Ȥˤ��ϥå������Ǥ� 100 �ʾ�ˤ��뤳�ȤǤ��������η�̤�����ˤϡ�-w N ���ץ����ˤ�äƾ��ֶ��֤Υ����������Τˤ��ʤ��Υ���ԥ塼���dz����Ǥ���ºݤΥ����̤�Ŭ������Τˤ��뤳�ȤǤ����ǥե���ȤǤ� N �� 22 �ǡ�������б�������ֶ��֤� 4MB �Ǥ������Ȥ��С����ʤ��Υ���ԥ塼���� 128 MB �Υ������äƤ����硢-w27 �Ȼ��ꤹ����ˤ��¿���ξ��֤ˤĤ���Ĵ�٤�����Ǥ���Ǥ��礦��

�ޤȤ��Summary��

���Υޥ˥奢��κǽ����ʬ�Ǥϡ���Ʊ���ǡ����̿��˸¤餺 Promela �Ȥ���̾�θ���ˤ���¹ԥ����ƥ�Υ�ǥ��ɽ��ˡ�ˤĤ����������ޤ��������θ���Ϥ����Ĥ��Τ���äȤ���ä���ħ����äƤ��ޤ����ץ������֤��̿��ϡ���å���������ͭ�ѿ���𤷤ƹԤ��ޤ���Ʊ������Ʊ���̿��Ϥɤ������̲�������å������̿��ε����� 2 �ĤΥ������Ȥ��ƥ�ǥ벽����ޤ���Promela �Τ��٤Ƥ�ʸ������Ū�˥�ǥ��֥��å��������ǽ��������ޤ�������Ϥ���ʸ���¹Բ�ǽ�����¹��Բ�ǽ���ˤ�ꡢ�ۤȤ�ɤΥ������ϥץ����������äƤ���Ķ��ξ��֤ˤ��ޤ����ץ�����Ʊ�Τ���ߺ��Ѥȥץ�������Ĵ�Ϥ��θ���κ���ˤ����ΤǤ���Promela ���߷ס�Spin �ˤ�븡�ڤȤ��α����ϰϤˤĤ��Ƥξܺ٤ϡ�[5] �ˤ���ޤ���

Promela �ϡ��ץ���������ǤϤʤ��������ѤΥ�ǥ�󥰸����տޤ��ƺ���Ƥ��ޤ����㤨�С���ι������ݥǡ������ϴޤ�Ǥ��ޤ��󤷡��ѿ��δ��ܷ���鷺����������ޤ��󡣸��ڥ�ǥ�ϥץ��ȥ���μ�������ݲ�������ΤǤ�����ݲ��ˤ�ꡢ�ץ���������ߺ��Ѥ��ܼ�Ū���Ǥ�ʬΥ����Ĵ����������Ǥ���ΤǤ�����ݲ��ˤ������ȥץ�����ߥ󥰤˴ؤ���ܺ٤��ޤ�����ΤǤ���

Promela �μ�������������ι�ʸ�Ϥ������äѤ� C ���� [6] ����äȤ��Ƥ��ޤ���Promela �� E.W. ���������ȥ� [1] �� C.A.R. �ۡ��� [3] �� "�����ɥ��ޥ�ɸ���" �αƶ����礤�˼����Ƥ��ޤ����������������ȤϽ���ʰ㤤������ޤ������������ȥ�θ���ϥץ���������ߺ��Ѥ����Υץ�ߥƥ��֤Ȥ��ƻ��äƤ��ޤ��󡣥ۡ����θ���ϡ�Ʊ���̿��Τߤ�١����Ȥ��Ƥ��ޤ����ޤ��ۡ����θ���Ǥϡ������ɤ���ǻ��ѤǤ���ʸ�μ�������¤�����ޤ���Promela ������Ƚ۴�ʸ�ΰ�̣�ϡ�¾�Υ����ɥ��ޥ�ɸ���Ȱۤʤ�ޤ������٤ƤΥ����ɤ����ΤȤ��ϡ�����ʸ�����Ǥ����ΤǤϤʤ��֥��å�����ޤ���ɬ�פǤ����Ʊ�����Ȥ��ޤ��ˡ�

�桼���ϺǾ��¤����Ϥ򤹤�����ǡ�Promela �θ��ڥ�ǥ뤫���������줿���ڥץ��������������뤳�Ȥ��Ǥ��ޤ���Spin ���ȡ���������������븡�ڥץ������ɤ���� ANSI C �ǵ��Ҥ���Ƥ��뤿�ᡢUnix �����ƥ�֤ǰܿ�����ǽ�Ǥ��������ϡ��ۥ��ȥ���ԥ塼����ʪ��Ū�ʸ³�������Ф��褦�˳���̾��Ǥ����ץ��ȥ���θ��ڤˤ����Ƥ������¤���ǤǤ���������θ��ڤ�¸������ΤǤ���

��Ͽ�����ڥ������Ȥι��ۡ�Appendix: Building a Verification Suite��

Exercises.html �� Roadmap.html �⸫�Ƥ���������

Spin ��Ȥä����ڤˤ����Ƥޤ����ˤ��ʤ���Фʤ�ʤ��Ż��ϡ�����������¤ʥ�ǥ�� Promela �ˤ�국�Ҥ��뤳�ȤǤ������θ���Ϥ虜�Ⱦ���������Ƥ��ޤ�����ǥ�󥰤���Ū��Ĵ�����٤���Ĵ����˴ؤ��륷���ƥ��¦�̤���Ф�����Ǥ���¾�ξܺ���ʬ�ϡ��ξݤ��ޤ�������Ū�ˤϡ���ǥ�Ͻ̾��ǤΥ����ƥ�Ǥ��ꡢ���ڤ��������˴ؤ�����ʬ�����ե륷���ƥ�������Ǥ���ɬ�פ�����ޤ������ä����ǥ���ۤ���ȡ�����ϡ����������򸡾ڤ��뤿��˻Ȥ��롢����줬 "���ڥ�������" �ȸƤְ�Ϣ�ι���ʪ�δ��פȤʤ�ޤ������ڥ������Ȥ��ۤ��뤿��ˡ���ǥ�� assert ��ųݤ�������Ǥ��ޤ���assert �ˤ�ꡢ��ǥ������ѿ����ͤ䥤�٥�ȤΥ������󥹤˴ؤ������Ѿ�����������뤳�Ȥ��Ǥ��ޤ���

�ʲ��Ǽ��夲��ǽ����ϡ������֤��Τ˵������졢1966 ǯ�� H. Hyman �� Communications of the ACM ��ȯɽ������¾�����������Ф����Ǥ���

  1 Boolean array b(0;1) integer k, i,
  2 comment process i, with i either 0 or 1, and k = 1-i;
  3 C0:	b(i) := false;
  4 C1:	if k != i then begin;
  5 C2:	if not b(1-i) then go to C2;
  6 	else k := i; go to C1 end;
  7 	else critical section;
  8 	b(i) := true;
  9 	remainder of program;
 10 	go to C0;
 11 	end

���β�ϡ�Dekker �ν���β�Ȥ����Τ����Τǡ�2 �ĤΥץ��������ֹ� 0 �� 1�ˤ��оݤȤ�����ΤǤ������ޡ�Hyman �β򤬥���ƥ����륻���������Ф��륢����������¾����������ݾڤ��Ƥ����������������Ȥ��ޤ��礦�������κǽ�λŻ��ϡ�Promela �Ǥ��β�Υ�ǥ������Ǥ��������ǡ����β�ǻȤ��Ƥ����ѿ����Ф���̾������狼��䤹����Τˤ��ޤ���

   1  bool want[2];	/* Bool array b */
   2  bool turn;	/* integer    k */
   3  
   4  proctype P(bool i)
   5  {
   6  	want[i] = 1;
   7  	do
   8  	:: (turn != i) ->
   9  		(!want[1-i]);
  10  		turn = i
  11  	:: (turn == i) ->
  12  		break
  13  	od;
  14  	skip; /* critical section */
  15  	want[i] = 0
  16  }
  17  
  18  init { run P(0); run P(1) }

���Υ�ǥ�θ��ڥץ�����������������ѥ��뤹�뤳�Ȥǡ��ǥåɥ��å��Τ褦�ʼ��פ����꤬����С�����򸫤Ĥ�������Ǥ��ޤ���

	$ spin -a hyman0
	$ gcc -o pan pan.c
	$ ./pan
	full statespace search for:
	assertion violations and invalid endstates
	vector 20 byte, depth reached 19, errors: 0
	      79 states, stored
	       0 states, linked
	      38 states, matched	total: 117
	hash conflicts: 4 (resolved)
	(size 2^18 states, stack frames: 3/0)
	
	unreached code _init (proc 0):
		reached all 3 states
	unreached code P (proc 1):
		reached all 12 states

���Υ�ǥ�Ϻǽ�Υƥ��Ȥ˥ѥ����ޤ�����������������줬�����˶�̣������Τϡ����Υ��르�ꥺ�ब��¾������ݾڤ��Ƥ��뤫�ɤ������ˤĤ��ƤǤ�������ˤϤ����Ĥ�����ˡ������ޤ������Ǥ��ñ����ˡ��ñ����������ɽ������ assert ���ǥ�˲ä��뤳�ȤǤ���

   1  bool want[2];
   2  bool turn;
   3  byte cnt;
   4  
   5  proctype P(bool i)
   6  {
   7  	want[i] = 1;
   8  	do
   9  	:: (turn != i) ->
  10  		(!want[1-i]);
  11  		turn = i
  12  	:: (turn == i) ->
  13  		break
  14  	od;
  15  	skip; /* critical section */
  16  	cnt = cnt+1;
  17  	assert(cnt == 1);
  18  	cnt = cnt-1;
  19  	want[i] = 0
  20  }
  21  
  22  init { run P(0); run P(1) }

�����Ǥϡ��������Х��ѿ� cnt ���ɲä�������ƥ����륻�������˿��������Ȥ��� +1������ƥ����륻������󤫤�Ǥ�Ȥ��� -1 ����褦�ˤ��ޤ����������ѿ����ͤ��Ȥꤦ������ͤ� 1 �Ǥ��ꡢ�ҤȤĤΥץ�����������ƥ����륻���������ˤ���Ȥ��Τ� 1 �ˤʤ�ޤ���

	$ spin -a hyman1
	$ gcc -o pan pan.c
	$ ./pan
	assertion violated (cnt==1)
	pan: aborted (at depth 15)
	pan: wrote pan.trail
	full statespace search for:
	assertion violations and invalid endstates
	search was not completed
	vector 20 byte, depth reached 25, errors: 1
	     123 states, stored
	       0 states, linked
	      55 states, matched	total: 178
	hash conflicts: 42 (resolved)
	(size 2^18 states, stack frames: 3/0)

���ڥץ������� assert ��ȿ�����ä�����𤷤Ƥ��ޤ������Υ��顼�������󥹤�����å����뤿��� Spin �� -t ���ץ�������ꤷ�Ƥ��ε��פ򸫤Ƥߤޤ��礦��

	$ spin -t -p hyman1
	proc  0 (_init)	line 24 (state 2)
	proc  0 (_init)	line 24 (state 3)
	proc  2 (P)	line 8 (state 7)
	proc  2 (P)	line 9 (state 2)
	proc  2 (P)	line 10 (state 3)
	proc  2 (P)	line 11 (state 4)
	proc  1 (P)	line 8 (state 7)
	proc  1 (P)	line 12 (state 5)
	proc  1 (P)	line 15 (state 10)
	proc  2 (P)	line 8 (state 7)
	proc  2 (P)	line 12 (state 5)
	proc  2 (P)	line 15 (state 10)
	proc  2 (P)	line 16 (state 11)
	proc  2 (P)	line 17 (state 12)
	proc  2 (P)	line 18 (state 13)
	proc  1 (P)	line 16 (state 11)
	proc  1 (P)	line 17 (state 12)
	spin: "hyman1" line 17: assertion violated
	step 17, #processes: 3
			want[0] = 1
			_p[0] = 12
			turn[0] = 1
			cnt[0] = 2
	
	proc  2 (P)	line 18 (state 13)
	proc  1 (P)	line 17 (state 12)
	proc  0 (_init)	line 24 (state 3)
	3 processes created

���ơ��⤦�ҤȤĤΥ��顼��ȯ����ˡ�򸫤Ƥߤޤ��礦���⤦���٥�ǥ�˥���ƥ����륻���������Υץ������ο��˴ؤ�������ä��ޤ���

   1  bool want[2];
   2  bool turn;
   3  byte cnt;
   4  
   5  proctype P(bool i)
   6  {
   7  	want[i] = 1;
   8  	do
   9  	:: (turn != i) ->
  10  		(!want[1-i]);
  11  		turn = i
  12  	:: (turn == i) ->
  13  		break
  14  	od;
  15  	cnt = cnt+1;
  16  	skip;	/* critical section */
  17  	cnt = cnt-1;
  18  	want[i] = 0
  19  }
  20  
  21  proctype monitor()
  22  {
  23  	assert(cnt == 0 || cnt == 1)
  24  }
  25  
  26  init {
  27  	run P(0); run P(1); run monitor()
  28  }

���٤ϡ������� cnt ���ͤ˴ؤ������Ѿ��ϡ���Ω�����ץ����� monitor() ��̾�����ä˰�̣�Ϥʤ��ΤǤ����ˤˤ�����ޤ����������ɲä��줿�ץ������ϡ�2 �ĤΥץ������ȤȤ������ޤ������Υץ������� 1 ���ƥåפ�¹Ԥ���λ���ޤ���������ϥ����ƥ�μ¹�����ɤΥ����ߥ󥰤Ǥ��¹Ԥ����ǽ��������ޤ���Promela �ˤ���ǥ벽���줿�����ƥࡢ����ӡ�Spin �ˤ�긡�ڤ���륷���ƥ�ϡ���������Ʊ���Ǥ�����äơ�Spin �ˤ�븡�ڤ� 3 �ĤΥץ������β�ǽ�����٤Ƥ������ߥ󥰤򸡾ڤ��оݤȤ��뤿�ᡢ���� assert ��¾�� 2 �ĤΥץ���������¸���֤Τ����륿���ߥ󥰤�ɾ�������ΤǤ����⤷���ڥץ�����ब��ȿ����𤷤ʤ��ä����ϡ������� assert ��ȿ���Ȥ��褦�ʼ¹ԥ������󥹤���3 �ĤΥץ������μ¹ԥ��ԡ��ɤˤ�餺�ˤޤä����ʤ����Ȥȷ����Ť�������Ǥ���ΤǤ���monitor �ץ������ˤ�륷���ƥ�����Ѿ���������������å�������ˡ���������줿��ˡ�Ǥ������ڥץ������ϰʲ��Τ褦�ʷ�̤���𤹤�Ǥ��礦��

	$ spin -a hyman2
	$ gcc -o pan pan.c
	$ ./pan
	assertion violated ((cnt==0)||(cnt==1))
	pan: aborted (at depth 15)
	pan: wrote pan.trail
	full statespace search for:
	assertion violations and invalid endstates
	search was not completed
	vector 24 byte, depth reached 26, errors: 1
	     368 states, stored
	       0 states, linked
	     379 states, matched	total: 747
	hash conflicts: 180 (resolved)
	(size 2^18 states, stack frames: 4/0)

2 �ĤΥץ������� 3 ���ܤ� monitor �ץ������Ȥ�;ʬ�ʥ��󥿡��꡼�ӥ󥰤Τ��ᡢõ�����٤������ƥ���ֿ��������Ƥ��ޤ��������顼����������𤵤�Ƥ��ޤ���

�⤦�ҤȤĤ��� (Another Example��

�����ƥ�������������ĤǤ⥰�����Х�����Ѿ��Ȥ�����������Ϳ������Ȥ������ǤϤ���ޤ��󡣤�����Ϥ���򼨤�����ΤǤ��������ñ��ʥӥåȸ򴹥ץ��ȥ����alternating bit protocol�ˤǡ���å�������»�����椬�ߤ��ǥ�󥰤������������negative acknowledgements�ˤˤ���ĥ������ΤǤ���

   1  #define MAX	5
   2  
   3  mtype = { mesg, ack, nak, err };
   4  
   5  proctype sender(chan in, out)
   6  {	byte o, s, r;
   7  
   8  	o=MAX-1;
   9  	do
  10  	:: o = (o+1)%MAX; /* next msg */
  11  again: if
  12         :: out!mesg(o,s) /* send */
  13         :: out!err(0,0)  /* distort */
  14         :: skip       /* or lose */
  15         fi;
  16         if
  17         :: timeout   -> goto again
  18         :: in?err(0,0) -> goto again
  19         :: in?nak(r,0) -> goto again
  20         :: in?ack(r,0) ->
  21  		if
  22  		:: (r == s) -> goto progress
  23  		:: (r != s) -> goto again
  24  		fi
  25         fi;
  26  progress:	s = 1-s	/* toggle seqno */
  27  	od
  28  }
  29  
  30  proctype receiver(chan in, out)
  31  {	byte i;		/* actual input   */
  32  	byte s;		/* actual seqno   */
  33  	byte es;	/* expected seqno */
  34  	byte ei;	/* expected input */
  35  
  36  	do
  37  	:: in?mesg(i, s) ->
  38  		if
  39  		:: (s == es) ->
  40  			assert(i == ei);
  41  progress:		es = 1 - es;
  42  			ei = (ei + 1)%MAX;
  43  			if
  44  	/* send,   */	:: out!ack(s,0)
  45  	/* distort */	:: out!err(0,0)
  46  	/* or lose */	:: skip
  47  			fi
  48  		:: (s != es) ->
  49  			if
  50  	/* send,   */	:: out!nak(s,0)
  51  	/* distort */	:: out!err(0,0)
  52  	/* or lose */	:: skip
  53  			fi
  54  		fi
  55  	:: in?err ->
  56  		out!nak(s,0)
  57  	od
  58  }
  59  
  60  init {
  61  	chan s_r = [1] of { mtype,byte,byte };
  62  	chan r_s = [1] of { mtype,byte,byte };
  63  	atomic {
  64  		run sender(r_s, s_r);
  65  		run receiver(s_r, r_s)
  66  	}
  67  }

���Υץ��ȥ��뤬�������ǡ�����ž������Ȥ���̿���ƥ��Ȥ��뤿��ˡ����Υ�ǥ�ˤϤ��Ǥˤ����Ĥ��� assert ����������Ƥ��ޤ���sender �ϥ�å������Ȥ��� MAX ��ˡ�Ȥ����;����ʤ�̵�����ž������褦���������Ƥ��ޤ���MAX ���ͤϽ��פǤϤʤ����ץ��ȥ������ǥ��������ֹ�����ʺ��Υ������Ǥ� 2�ˤ���礭����в��Ǥ⤫�ޤ��ޤ��󡣤��Ȥ���å�������»���β�ǽ�����������Ȥ��������줿�ǡ������ä����ꡢ�¤��ؤ���줿�ꤹ�뤳�Ȥʤ� receiver ���Ϥ����뤳�Ȥ����ڤ������ΤǤ���40 ���ܤ� assert �ˤ�����Τˤ���򸡾ڤ��ޤ����⤷�嵭�˽񤤤��׵᤬�������ʤ���ǽ����������ϡ����� assert �ΰ�ȿ�����Ф���ޤ���

�ǽ�θ��ڤǤϡ��������ä�����β�ǽ�����ʤ���������¿������Ƥ���ޤ���

	$ spin -a ABP0
	$ gcc -o pan pan.c
	$ ./pan
	full statespace search for:
	assertion violations and invalid endstates
	vector 40 byte, depth reached 131, errors: 0
	     346 states, stored
	       1 states, linked
	     125 states, matched	 total: 472
	hash conflicts: 17 (resolved)
	(size 2^18 states, stack frames: 0/25)
	
	unreached code _init (proc 0):
		reached all 4 states
	unreached code receiver (proc 1):
		line 58 (state 24)
		reached: 23 of 24 states
	unreached code sender (proc 2):
		line 28 (state 27)
		reached: 26 of 27 states

���������դ��Ƥ������������η�̤��������줿��å����������������֤��Ϥ���줿���Ȥ��̣���Ƥ���Τˤ����ޤ��󡣤����ϥǡ��������ʤ餺ž�������Ȥ������Ȥϥ����å����Ƥ��ޤ���sender �� receiver ������ͭ���ʥ�å����������餺���顼��å�������򴹤��Ƥ��뤰��ޤ�äƤ����ǽ���⤢��ޤ������������å����뤿��ˡ�sender �� receiver ���ߥ�������ʤ����ʤ��Ƥ��뤳�Ȥ򼨤��ƥץ������ξ��֤� "�ץ����쥹����" �Υ�٥��Ϥ�ޤ��ʼºݤˤ������Υץ����������ǽ�ʬ�ʤΤǤ����ˡ�

����ǥץ����쥹���֤�ޤä����̲ᤷ�ʤ��ޤ޼¹ԥ������뤬�����֤��������ʤ����򸡾ڤǤ���褦�ˤʤ�ޤ�������μ¹ԥե�����Ϥ��Τޤ޻Ȥ��ʤ��Τǡ��Υ�ץ����쥹��������򸫤Ĥ��뤿��˸��ڥץ������򥳥�ѥ��뤷�ʤ����ޤ���

	$ gcc -DNP -o pan pan.c
	$ ./pan -l
	pan: non-progress cycle (at depth 6)
	pan: wrote pan.trail
	full statespace search for:
	assertion violations and non-progress loops
	search was not completed
	vector 44 byte, depth reached 8, loops: 1
	      12 states, stored
	       1 states, linked
	       0 states, matched	total: 13
	hash conflicts: 0 (resolved)
	(size 2^18 states, stack frames: 0/1)

��̤ˤ��ȡ����ʤ��Ȥ�ҤȤĤΥΥ�ץ����쥹�������뤬����ޤ����ǽ�˸��Ĥ�����Τϸ��ڥץ������ˤ�� trail �ե�����ˤ��ε��פ���¸����Ƥ��ơ������򤽤�򸫤�����Ǥ��ޤ������η�̤�� 2 ����Ⱦ�˼����ޤ�����å������Τ椬�ߤ�»�������٤ⷫ���֤�³�����Ƥ��ꡢ���¥��顼�Ǥ��������顼�������󥹤Ȥ��ƤϤ��ޤ����򤯤���ޤ��󡣥Υ�ץ����쥹�������뤬������¸�ߤ���Τ����뤿��ˡ�-c �ե饰��ȤäƤߤޤ���-c ���ץ����ΰ����� 0 �����ꤷ�����ϡ����顼�ι�׿������Ϥ���ޤ���

	$ pan -l -c0
	full statespace search for:
	assertion violations and non-progress loops
	vector 44 byte, depth reached 137, loops: 92
	     671 states, stored
	       2 states, linked
	     521 states, matched	 total: 1194
	hash conflicts: 39 (resolved)
	(size 2^18 states, stack frames: 0/26)

���顼�ϡ�92 ����������ޤ���-c ���ץ����� -c1, -c2, -c3, ... �Τ褦�˽�˻ȤäƤ��Υ������󥹤�ҤȤĤ��ĸ�������Ǥ��ޤ������������ǽ�˸��Ĥ��ä���å�������»���򷫤��֤����򸶰��Ȥ��륨�顼�������󥹤�������ơ��������٤����򸺤餹���Ȥ��Ǥ��ޤ������Τ���� "progress" �� 8 ʸ������Ϥޤ���Ƭ���Ĥ�����٥���å�������»�����Ƥ���ƹԡ�13, 43, 48 ���ܡˤ�ĥ�ꡢ�Ĥ륨�顼��������򸫤ޤ��ʥ�٥�� :: �θ�����������ޤ���*4��

	$ spin -a ABP1
	$ gcc -DNP -o pan pan.c
	
	$ ./pan -l
	pan: non-progress cycle (at depth 133)
	pan: wrote pan.trail
	
	full statespace search for:
	assertion violations and non-progress loops
	search was not completed
	
	vector 44 byte, depth reached 136, loops: 1
	
	     148 states, stored
	       2 states, linked
	       2 states, matched	 total: 152
	
	hash conflicts: 0 (resolved)
	(size 2^18 states, stack frames: 0/26)

���٤ϡ��������줿���פˤ�ꤳ�Υץ��ȥ���ˤ����뿿�˿���ʥХ������餫�ˤ��뤳�Ȥ��Ǥ��ޤ����� 2 �θ�Ⱦ�ˤ��ε��פ򼨤��ޤ���

      $ spin -t -r -s ABP0
      <<<<>>>>
      proc  1 (sender)   line  13, Send err,0,0 -> queue 2 (out)
      proc  2 (receiver) line  55, Recv err,0,0 <- queue 2 (in)
      proc  2 (receiver) line  56, Send nak,0,0 -> queue 1 (out)
      proc  1 (sender)   line  19, Recv nak,0,0 <- queue 1 (in)
      spin: trail ends after 12 steps
      step 12, #processes: 3
		_p[0] = 6
      proc  2 (receiver)	line 36 (state 21)
      proc  1 (sender)	line 11 (state 6)
      proc  0 (_init)	line 67 (state 4)
      3 processes created
      $ 
      $ spin -t -r -s ABP1
      ...
      proc  2 (receiver) line  39, Recv mesg,0,0 <- queue 2 (in)
      proc  2 (receiver) line  47, Send err,0,0  -> queue 1 (out)
      proc  1 (sender)   line  20, Recv err,1,0  <- queue 1 (in)
      proc  1 (sender)   line  12, Send mesg,0,0 -> queue 2 (out)
      proc  2 (receiver) line  39, Recv mesg,0,0 <- queue 2 (in)
      proc  2 (receiver) line  52, Send nak,0,0  -> queue 1 (out)
      proc  1 (sender)   line  21, Recv nak,0,0  <- queue 1 (in)
      proc  1 (sender)   line  12, Send mesg,0,0 -> queue 2 (out)
      proc  2 (receiver) line  39, Recv mesg,0,0 <- queue 2 (in)
      proc  2 (receiver) line  52, Send nak,0,0  -> queue 1 (out)
      <<<<>>>>
      proc  1 (sender)   line  21, Recv nak,0,0  <- queue 1 (in)
      proc  1 (sender)   line  12, Send mesg,0,0 -> queue 2 (out)
      proc  2 (receiver) line  39, Recv mesg,0,0 <- queue 2 (in)
      proc  2 (receiver) line  52, Send nak,0,0  -> queue 1 (out)
      spin: trail ends after 226 steps
      ...

	�� 2. ���顼�ε��� - ��ĥ���� Alternating Bit Protocol

�ҤȤĤΡ������򼨤���acknowledgment ���椬�����ž�������ȡ�sender �� receiver ��̵�¥�������˴٤äƤ��ޤ��ޤ���sender �� acknowledgment �������äƤ��ʤ��ΤǴ�Ǥ˺Ǹ�����ä���å������򷫤��֤��������ޤ����ޤ���receiver ��ޤ���Ǥ����������negative acknowledgment�ˤ�������ݤ�³���ޤ���

����˿������겼�����Digging Deeper��

���Υޥ˥奢��� Spin �μ��פʵ�ǽ�γ��פȸ��ڤǻȤ��������Ū�ʤ�����ˤĤ����������Ƥ���ˤ����ޤ���Spin �ˤϡ������Ǽ��夲����ΰʳ��ˤ⡢���ڤ������Ω���������Τ����Ω�ĤǤ�������������ε�ǽ������ޤ���

Spin �ǤϤޤ� "������" �� "�׵�" �� never-claim �ǥ�ǥ벽���뤳�Ȥǥ����ƥब��������������ɤ������ڤ��뤳�Ȥ�Ǥ��ޤ����桼���������ƥबã�����٤������������������ claim ��ɽ������ȡ�Spin �����᤯���� claim ������Ω�Ļ���������뤫��ȿ��򼨤��Ǥ��礦��never-claim ��B���chi�����ȥޥȥ�*5�������ǡ���������������Ĥ��ä�������ǥ벽��ǽ�Ǥ����������С������� Spin �Ǥϡ��׵���������Τ� LTL �ι�ʸ��Ȥ������Ǥ��ޤ���Spin �ϥ桼����������� LTL �򤽤�������� never-claim ���Ѵ����뤳�Ȥ��Ǥ��ޤ���

Spin �ǤϤޤ����桼��������������֥��åȤ�õ�������¤���褦�˥����ƥ�ξ��ֶ��֤�̾���������Ǥ��ޤ��ʤ����Ǥ� never-claim ����Ѥ��ޤ��������٤Ͼ��ֶ��֤��ڤ��뤿��˻��Ѥ��ޤ��ˡ�������ˡ�ˤ�ꡢ���Ȥ������ֶ���õ�����¹��Բ�ǽ�Ǥ⡢�����ƥ�ο����񤤤�Ϳ�������顼�Υѥ����󤬴ޤޤ�뤫�ɤ����򤹤Ф䤯���ڤ��뤳�Ȥ��Ǥ��ޤ���

����� Promela �� Spin ���̤λ�����ˡ�ˤĤ��Ƥξܺ٤ˤĤ��Ƥϡ�[5] �򻲹ͤˤ��Ƥ���������Spin �С������ 2.0 �� 3.0 �Ǥγ�ĥ�ˤĤ��Ƥ� WhatsNew.html �򸫤Ƥ���������

����ʸ����References��

[1] Dijkstra, E.W., ``Guarded commands, non-determinacy and formal derivation of programs.'' CACM 18, 8 (1975), 453-457.
[2] Dijkstra, E.W., ``Solution to a problem in concurrent programming control.'' CACM 8, 9 (1965), 569.
[3] Hoare, C.A.R., ``Communicating Sequential Processes.'' CACM 21, 8 (1978), 666-677.
[4] Holzmann, G.J., ``Algorithms for automated protocol verification.'' AT&T Technical Journal 69, 1 (Jan/Feb 1990). Special Issue on Protocol Testing, Specification, Verification.
[5] Holzmann, G.J., The Spin Model Checker: Primer and Reference Manual (2003), Addison-Wesley.
[6] Kernighan, B.W. and Ritchie, D.M., The C Programming Language. 2nd ed. (1988), Prentice Hall.


*1 ���� : �Ƕ�ΥС������ʳ�ǧ�����Τ� Version 4.2.9 -- 8 February 2007�ˤǤ�ɬ������ init �ץ��������������ɬ�פϤ���ޤ��󡣰ʲ��Τ褦�˥ץ��������������Ƭ�� active ��Ĥ��뤳�Ȥǥץ�����൯ư���˥ץ������Υ��󥹥��󥹤�������������Ǥ��ޤ���
	byte state = 2;

	active proctype A()
	{	(state == 1) -> state = 3
	}

	active proctype B()
	{	state = state - 1
	}

*2 ���� : Version 2 �� atomic �ΰ�̣���ѹ����줿���ᡢatomic �������󥹤���ǥ֥��å����Ƥ��󥿥��२�顼�ȤϤʤ�ޤ��󡣤⤷ atomic �������󥹤���ǥץ��������֥��å�������硢¾�Υץ������Τ����ҤȤĤ������Ū�����򤷼¹Ԥ��ޤ������θ�֥��å����Ƥ���ʸ���¹Բ�ǽ�ˤʤ�ȡ��ץ������ϻĤ�Υ������󥹤��Բ�ʬ�˼¹Ԥ�������Ǥ��ޤ����ʤ�������¾�Υץ�������¹Բ�ǽ�ʾ��ϡ��ɤΥץ��������¹Ԥ���뤫�������Ū�Ǥ��ˡ����� atomic ���ѹ���ȼ�äơ�d_step ���������ɲä���ޤ�����atomic ��Ʊ�͡�d_step �ǰϤޤ줿�������󥹤��Բ�ʬ�˼¹Ԥ�������Ǥ��ޤ������������˼���3�Ĥ����󤬤���ޤ���1. �������󥹤ϴ����˷���Ū�Ǥ��뤳�ȡ�2. d_step �γ��˽ФƹԤ� goto �����פ�ޤޤʤ����ȡ�3. d_step �γ��������äƤ����٥��ޤޤʤ����ȡ��Ǥ����ޤ���d_step �������󥹤���ǥ֥��å��������ϥ�󥿥��२�顼�Ȥʤ�ޤ����ܤ����ϡ�WhatsNew.html �� 2.1.3 d_step ����� 2.3.1 Blocking Atomic Sequences ������������ޤ���

*3 ���� : ��ʸ�Ǥϡ�"For instance, if by adding a label to the process type dijkstra(), from section 1.9:" �ȤʤäƤ��ޤ�����Gerard J. Holzmann �˳�ǧ�����Ȥ���������ϴְ㤤����ʸ��� 1.9 ��Ϥ���ޤ���ʸ�ʸ�⽤������ޤ�����2007.06.03�ˡ�

*4 ���� : �Ƕ�ΥС������ʳ�ǧ�����Τ� Version 4.2.9 -- 8 February 2007�ˤǤ� :: ��ľ��˥�٥�������Ȱʲ��Τ褦�˥��顼�ˤʤ�ޤ���
	$ spin -a ABP0
	error: ("ABP0":13) label progress_0 placed incorrectly
	=====>instead of
		do (or if)
		:: ...
		:: Label: statement
		od (of fi)
	=====>always use
	Label:	do (or if)
		:: ...
		:: statement
		od (or fi)
Gerard J. Holzmann ��
   :: skip -> progress_1: out!err(0,0)
�Ȥ����褦�ˤ���Ф����ȶ����Ƥ�餤�ޤ�������å�������»�����Ƥ���ԡ�14, 52���ܡˤ���ӥ��顼���������Ƥ���ԡ�13, 51���ܡˤ˥ץ����쥹��٥����������ȡ���ʸ����������Ƥ��뿿�˿���ʥХ��Υ��顼�������󥹤������ޤ����ʲ��˥ץ����쥹��٥������������ǥ�򼨤��ޤ���
   1  #define MAX	5
   2	
   3	mtype = { mesg, ack, nak, err };
   4	
   5	proctype sender(chan in, out)
   6	{	byte o, s, r;
   7		
   8		o=MAX-1;
   9		do
  10		  :: o = (o+1)%MAX; /* next msg */
  11	again:	     if
  12		       :: out!mesg(o,s) /* send */
  13		       :: skip -> progress_0: out!err(0,0)  /* distort */
  14		       :: skip -> progress_1: skip /* or lose */
  15		     fi;
  16		     if
  17		       :: timeout   -> goto again
  18		       :: in?err(0,0) -> goto again
  19		       :: in?nak(r,0) -> goto again
  20		       :: in?ack(r,0) ->
  21			  if
  22			    :: (r == s) -> goto progress
  23			    :: (r != s) -> goto again
  24			fi
  25		     fi;
  26	progress:	s = 1-s	/* toggle seqno */
  27		od
  28	}
  29	
  30	proctype receiver(chan in, out)
  31	{	byte i;		/* actual input   */
  32		byte s;		/* actual seqno   */
  33		byte es;	/* expected seqno */
  34		byte ei;	/* expected input */
  35		
  36		do
  37		  :: in?mesg(i, s) ->
  38		     if
  39		       :: (s == es) ->
  40			  assert(i == ei);
  41	progress:	  es = 1 - es;
  42			  ei = (ei + 1)%MAX;
  43			  if 
  44			    :: out!ack(s,0) /* send,   */	
  45			    :: out!err(0,0) /* distort */
  46			    :: skip /* or lose */
  47			  fi
  48		       :: (s != es) ->  
  49			  if
  50			    :: out!nak(s,0) /* send,   */
  51			    :: skip -> progress_0: out!err(0,0) /* distort */
  52			    :: skip -> progress_1: skip /* or lose */
  53			  fi
  54		     fi
  55		  :: in?err(0,0) ->
  56		     out!nak(s,0)
  57		od
  58	}
  59	
  60	init {
  61		chan s_r = [1] of { mtype,byte,byte };
  62		chan r_s = [1] of { mtype,byte,byte };
  63		atomic {
  64			run sender(r_s, s_r);
  65			run receiver(s_r, r_s)
  66		}
  67	}

*5 ���� : B���chi��"�ӥ塼��"�Ȥ�"�ӥ�å�"��ȯ�����ޤ���


Spin Online References
Promela Manual Index
Promela Grammar
Spin HomePage
(Page Updated: 30 August 2014)