X__text__TEXTrVܻT__data__DATAV[\Y|W__cstring__TEXT>\__bss__DATA__picsymbolstub2__TEXTR4__la_sym_ptr2__DATA""__nl_symbol_ptr__DATA`tD__textcoal_nt__TEXTԻ @h P00O0\US}u5E@$ED$D$$讷[]ÐUS$8u$cD$aD$$OD$rD$$'$D$$EE}u^ED$ U;t E EED$D$$萶E@EE뚋ED$D$$\D$$@D$$$$ԜD$$D$$ڵE}uDD$ D$E@D$E$ZE@E봍D$ D$D$$dD$ D$D$$ϴ8tjD$ D$D$$薴$kD$ D$D$$X$D$ D$D$$,D$$س$譳D$$D$$D$$D$ D$$轳8t$[]ÐUS$E8uLD$$bEE;|+ED$0D$$)EƍD$ D$D$$課بD$ D$D$$uD$ D$D$$I|f8tT@D$x$jiD$x$N|D$x$2eE}u'tURE$E@Eэ8u#t|f8t8D$x$觱əD$x$英D$ ED$ED$$8u7بD$ D$D$$Ѱ2بD$ D$D$$蝰@D$ D$D$$q$[]ÐUS$E}u,ED$E@D$E$wE@Ẽ$[]ÐUS$\LE}tq}}X}tM,8<D$ ,D$,D$H$良|D$ D$D$H$XD$ ,D$D$H$&D$ @D$,D$H$a|D$ D$D$H$轮D$ @D$D$H$舮DE}u#E@D$E$蓭E@EՍLE}tq}}C}t8,8D$ ,D$,D$H$ѭD$ ,D$D$H$蚭D$ @D$,D$H$_D$H$莭,D$D$H$d2D$ @D$D$H$D$ D$D$H$蹬L8u`8u `0D$ `D$`D$P$^HD$ dD$dD$P$'\D$ @D$@D$P$D$H$ND$ D$D$H$衫WD$ D$D$H$u\bD$ D$D$H$ID$ @D$D$H$ϖD$H$FӖD$H$*ٖD$H$D$x${~ND$H$تD$$E$D$H$親D$ (D$D$H$&D$H$UMD$H$9$[]US00D$ D$D$$谩[]ÐUWVSE䍃EU ;u۪8/U ;t۪8E܃}ueE U؉|u1 U؉DD$ U؉D$E܋$ڧED$E܋@$蠧E܋@@D$E D$ U؉DD$D$ת$蒨 U؉D  U؉ȃE܋@@ t4 U؉D$%D$X$蠦Q}E܋@@ U؉D$<D$X$ME܋@@E܋@@XD$ 8tT STTD$D$k$譥E؃E܋@EE܃}ucE܃x tOED$E܋@@$荥u0E܋@@D$ E D$D$ת$螦E܋@E땍UU[^_]ÐUS4hEUЍE<uE EE;E|hED$ED$ED$ED$ED$ ED$UЍED$E$*D$E$ΥE뎍Ec4[]ÐUS$t$"}uPEx@tE@@@0E E@0EEE}t$E@D$E@D$$ʣ$[]US5} +EfxtEfxtEfx  E@ Dždppu=p8tpD$E $^up@p븃pp@llukl@ hhu`hxt:ED$h@$ۢudD$E$w h@$hd땋l@$ldE@  uE@D$x$x$átt(xt8 txtӋE$Ex@tE D$$財$$袡ED$ ED$xD$5$xEfxE@  uE@D$x$x$ˠtt(xt8 txtӋE$Ex@tE D$$躠$$誠ED$ ED$xD$u$耠Ĵ[]ÐUSE}E}u,EEEx@Ex<E@@D$E$5ED$E$%E@ uZED$KD$E$؟^D$aD$D$ED$ ED$ED$E$EE@E&E}~KE}~.E}u EEEx@Ex<EHE; }u Ext}ExE@@D$E$|EtEfx@u8uED$ E D$eD$E$fED$kD$$GD$$/D$D$ED$ED$ D$ED$E$t`ED$KD$E$ӝ^D$aD$D$ED$ ED$ED$E$ED$E$蓝u)ED$ED$$?E@EEEEĔ[]US4u%8u/9D$E$JuD$E$5^D$E$D$E$ևD$E$D$E$ܝ5D$E$ǝ_D$E$貝jD$E$蝝nD$E$舝D$E$s%E}u_ED$D$E$<ED$D$$輛D$D$E$ވD$E$DžU;B |MЍA<u+D$ D$D$E$肜)D$ D$5D$E$WmaD$E$4sD$E$xD$E$ E@ EjD$E$D$E$қ4[]ÐUS4E@:@@ t}tED$ކD$E$ED$ E D$D$$肙ED$D$E$И`E@D$$Exu=ED$E D$ED$ D$D$E$e"D$E$KE@D$AD$E$,fD$E$ED$E D$ED$ D$D$E$ߙD$E$ʙD$E$赙QExu}ED$D$E$艙ED$E D$ED$ E D$D$E$TED$ E D$D$E$/DžU;B|D$ ED$!D$E$D$ED$E D$D$ED$ E D$MD$E$蜘D$ED$ E D$jD$E$m?4[]ÐUS$PD$E$D$E$ȖD$E$觖E}uEEEx@teEfxt[ED$E@@$QuED$MpD$}$z}E}kE@ u2N} t!E@D$ED$rp$x}}E@ED$pD$}$/z}EED$pD$}$y}EED$pD$}$y}EvEx8uED$p$rwED$ E@8D$pD$}$gy}ED$q$wExt&E@D$qD$}$y eD$}$x<[^_]US4EUЍE<unEEE;E|SED$E D$ ED$UЍED$E$x`D$E$jxE룍E{4[]ÐUSLlD$@y$'x} D$@y$xC}lD$@y$wlD$@y$wlD$@y$w[]UST蕿DžgD$ D$D$x$qf8t9ax8u,axD$UlD$x$w*axD$}lD$x$vaxD$lD$x$vaxD$lD$x$vExu1@;~@@ čExuiD$ D$lD$x$u@ D$ D$lD$x$u@} DžD$ D$lD$x$_ulD$x$CuD$lD$x$u$mD$x$t(mD$x$tDž;B |xЍAtG@t@ tXx tG3mD$x$tD$>mD$x$sD$KmD$x$shD$[mD$x$s@D$kmD$x$gs}D$ym$'qr@} DžD$mD$x$rD$mD$x$r@ mD$x$r$AmD$x$trmD$x$Xr5hD$ D$D$x$5xf8mD$x$qDž1x;|'mD$x$qō1`D$x$qnD$x$qDž1x;|;D$ D$nD$x$3q뱍hD$x$ q1nD$x$pS`@; @i@@8'@@`8' M`@_ `` ``2D[hjx$h@ FYf"Y:Ufth  FYf?["?Y:Ufth@ B` `  L` 0;FQdȴnz(4L` C`-@m@_Q`ȴ -@mm @Qȴ @Qȴ@_C`-9M]l}._9MS ` ۽JMXiX@g{8Q`ȴ qQȴ`6_` @`@cuc M#@c-8` X$ȴȴ%5F[dw@cm ȴSi"@e8- _ +G`#3` `Mz5&@n85&n 8Me@M[ `88 z5`  M   `         Y`      @ c 'p     M   [@     k @ck&c C`@f}c `c`;`k@` ` @`|5@Y(:SzY @ ` `8;M`Y%8@tY 8  _A]g@h _  @        !h *!@!_b!xv!!!!"%"0"`""ȴ"""k%"#)#ȴ@#i#}####$$.$>$`$$$$$$ %`%%% &@&˲&&ȴ&'@'k'|'''''( (C(Z(k(k('(( (((k )`))ȴ)) )) *k *D*P*k_`*z***+#+@+++%"++ȴ ,K,d,,&+,,+,-8 -`--8--.@.d,.ȴ+..+/h$/@///// 0I0U0h0v000000_ 1 1@1o1111 2`222_222 3`3334@44_444425`5f55`5@66666707B@7\7p7778@8888 9[9`9_99k'9((99:':-:`:::2;;.;A;S;b;;;; <F<Z<r<[<<<< =`====>@>>>>?@????? @B@&\@@@@ȴA!A8/A`AM$AAABȴB,Bȴ5`BAȴBBBȴBȴCBB%C>CCCCD*D8@DoDDDDDDE%E8@E&$EEEEEEFF@F@FȴFFF85>G GGG`G8ȴoGGG8GmF8G%H/H@H`HHHI@ImII8III=J-J@JȴJ JJJK5K[>K`KKKL L$`LLLLLY MPMdM{M5MM NNȴ@N`N}NNFNȴNȴNOȴ@OȴpOOȴOOOP@PPPPPQ,Q;QCSQ8aQtQQQYtQQ RKRȴRRRRS````` a@a8ȴ@adaaaaaȴ bHbbbbbcc cFc`cck'cdd%dc@d_dsddddde8>*e&@eeee@e fBfȴ`ffffg`f@gigfg8gg hEhk'Whhhhhhic&iih8@iiiiȴcj@jc`j8jjj kDk`k2kkkkll+l@l$llm ma@mzm8dmmmn3n`nnnȴnkn>o@ooop@pk'ep'pȴC(pp qGq`qqqq5r rHrGG N r_rGvrtQrrs& s`sssst`|8c t`tttk'tPtu'u@u$auuuu&u v@v[`v[vcvsvvvw(w$?w`wwwwx`v[,x%"$`xxx y yȴBy`y5yyz6z`zzzzȴz {a`{{{{|!|4|P|||||z| }|5 N`}}}Y ~Z~~~~~Rȴ `@NY ~ B&Y`Fȴȴȴ ȴ`ȴ `'@  O@Y[ ` y'@`Yօ)By@Ms&ņ܆YS I_YF8ȴY@dRxY@jȴ{ȴ_d Wl_d>Ί H` M$&@i݌cTI KȴhMIȴ KȴhMY5$@d}ȴ_ F`'ˏh Tc_nB[@ȴY@@B `Fȴ `4@B@_` Vb~ `@қ@@' ` _@ȴ̟ 2`5 @oBA$@ȴkȴkd,ȴ@B@ȴlȴB>@ ȴ`ĥȴ `BĦȴ@Bi @` Tȴ@|ȴF ȴ4SBAB@ `@$s~9Rȴ S G'` `9+9`#@sҴBҴ @Ƶܵ O` }_?Pkp7[9&@@@ȴ&@@_@,:GTbvɾ_@$g|B~ſֿ_x@hh3$`>@ȴ@ `2 ` `$>@ ȴ`$ȴ@ ˲?Kh `$ ` @.@aB 4`  s$M]$ p7[9ȴ p7@[92?]k@&@zB``k$ `$@ ~` ` 6`ȴȴF@c>@ȴ/F``` z``c` ` @1e+C˲۲Rȴ˲R `>C˲۲}##4B?Q$6Pm$ ȴEU$ȴE@eȴ/@ |'$,kt_7`>@ȴ ȴ`@@2$@$>@@ȴ$@@˲ ` $ `@ Nf ȴ1K` ? `ȴF`8` f] @i _!3Hk}`h Sj2d$ `2ȴd Xȴk G@%@g2dȴ&$>`w|!|4||dt,_CUq@f˲6z#;`P`tȴ ` - `   + @ t   @! }h , `     @ `   -8 ! ? L    r  }_ Z#@}_ DT @     h `h*!}_@ `[ &@'Y`}_[ ,@ &Y>}_W)8}#`)7}#` BB_t}_$3}#N`))7}#3[+`@_} @n !_1`h-E}#S & : U q     !Q@!ȴ!)!!! "K"d""")7}#"# }_#,#`#}## & : U q     #Q$ȴ@$)$!$$$% %)7}#@%c%}h~%x%%% }h%% &K&&%&& '`'I0 }>_''$'B'ȴ (Y`(($()@)u)))*$+*`****$* +Y@+B+ȴ+++_ ,,,,,- -^-|----- ..8.0.H.`.....}ȴ/@/ s/// 0H0`0 r00001M"111@1&`111111-1&2$2-8z82K2[2q22B2ȴ2222B2ȴ3h@333333 4A4[4>u4$44444!455ȴ-5`55555555556&6ȴ46!B6`6666666677617G7T7%a755555555556&6~777$7ȴ7 8ȴ`8468888B9$9@9d99%99999:'::5:;:W:c::6:;@;;;;;; <`<ȴ<h<k<=>/=9=$Q=====>7>E>ȴT>>>>;;;>?`<?.?H?b?|???ȴ_??@@3@}#C@`@ȴ@C@@ȴ AA@AxAAAABB B-B@BdBmBtB}BBBBBB C C`CCCCCcDD8-,D;D- KD_[DmD3@D@Dȴ EAIEaEhiE{EEE3@@E@ȴEAȴE`@@AH0E F`FFF FFF_FoFGȴ GKGG+GY_Hx>/=@HjHBHrH}#HHHh IGISI^I}#xIIȴIIII JJJ`JJJJJJK@KgK~KKKKKL)L8Ls`LLvLLBLL+ M`MMMMMMMN0N@h`NN=>N==N OE>h`OOOkO@gO P?PȴTPȴEgPrPPPxIgPPP>/=P$Q=PPQ@AH0`0  Q$Q@QQ QQzR-RCR NSRȴdR>}#vRRRS&S$,S`SSS T`TTT8TU@UnUUUU8UVB>.VFW XSVgVJX$`XXXXYX Yȴ.VM WY`Y%YYY ZZ/Z`ZZ%ZZ[&[@[h[[[[[[[\ !\)\F\Y\\$\ȴ]@]g]>}#/=x]$Q=]S T]TT8]2B^Y@^^ȴY^t^_^^__ȴ_._`_c__ ````tQ` aFaaab*b>b`bbbc)c@c+ycccc N$cc)ccdȴ$ dBdȴdȴd$}#Tdddd eRekcemeyeeeeeeeeee ef"f@ffQffffȴfgg g0g)>gMgZgngggQfgȴh@h[0gMgmhhhhi'i@iQjiiȴiiiij@jjjjkk@k$k)7kȴkdkkl%lȴ4lLlNl}#glolk(lˏlm mNmmmmmn nBAn}#`nnnnno@ooQoȴp@ptpp qNqqqq)7}#qr@r_ryrrrJJ s@sB_smhyss}#glssmsn tB(t}#9t+Et`ttttq)7_ryrt u@uZu}gu{ugluuu v)v@v`vvvkw w+[h6wGw`wI0wwxh1xBx`xxx )_ yRy`yyyyyzz3zNzhfzzz[zzz{#{@{m{{{|@||||} } T}hl}}}[zzz}#{~-~`~~|~ `} } h }h?Gw`wwt}chπ&h@my )k@cw+F  )D_Xb)7@nzƄ `˲@`@  ň@ȴ `ʉ˲  `ŠҊˏm}@F )@xDm Ga;:W:~@Ga;:W:~@x}{uglu)v`v D*}_`gu)<`ԑ@`|ߒ Mcy9I^rÔٔ@oЕ0`ɖ)+D[q_$ȴԗ~76)ȴ@)li Nȴȴɘ֘)c>ȴ[i@yeߙeee'e?W>`qtQ Z* yE ^)̛)/WHKe@  #if defined(VERI) && !defined(NOREDUCE) && !defined(NP) if (!state_tables#ifdef HAS_CODE && !readtrail#endif ) { printf("warning: for p.o. reduction to be valid "); printf("the never claim must be stutter-invariant\n"); printf("(never claims generated from LTL "); printf("formulae are stutter-invariant)\n"); } UnBlock; /* disable rendez-vous */#ifdef BITSTATE if (udmem) { udmem *= 1024L*1024L; SS = (uchar *) emalloc(udmem); bstore = bstore_mod; } else SS = (uchar *) emalloc(1L<<(ssize-3));#else hinit();#if defined(FULLSTACK) && defined(BITSTATE) onstack_init();#if defined(CNTRSTACK) && !defined(BFS) LL = (uchar *) emalloc(1L<<(ssize-3)); stack = ( Stack *) emalloc(sizeof(Stack)); svtack = (Svtack *) emalloc(sizeof(Svtack)); /* a place to point for Pptr of non-running procs: */ noptr = (uchar *) emalloc(Maxbody * sizeof(char));#ifdef SVDUMP if (vprefix > 0) write(svfd, (uchar *) &vprefix, sizeof(int));#ifdef VERI Addproc(VERI); /* never - pid = 0 */ active_procs(); /* started after never */#ifdef EVENT_TRACE now._event = start_event; reached[EVENT_TRACE][start_event] = 1; globinit();go_again: do_the_search(); if (--Nrun > 0 && HASH_CONST[++HASH_NR]) { printf("Run %%d:\n", HASH_NR); wrap_stats(); printf("\n"); memset(SS, 0, 1L<<(ssize-3));#if defined(CNTRSTACK) memset(LL, 0, 1L<<(ssize-3));#if defined(FULLSTACK) memset((uchar *) S_Tab, 0, maxdepth*sizeof(struct H_el *)); nstates=nlinks=truncs=truncs2=ngrabs = 0; nlost=nShadow=hcmp = 0; Fa=Fh=Zh=Zn = 0; PUT=PROBE=ZAPS=Ccheck=Cholds = 0; goto go_again;}#ifdef HAS_PROVIDEDint provided(int, uchar, int, Trans *);intPrintf(const char *fmt, ...){ /* Make sure the args to Printf * are always evaluated (e.g., they * could contain a run stmnt) * but do not generate the output * during verification runs * unless explicitly wanted * If this fails on your system * compile SPIN itself -DPRINTF * and this code is not generated */ if (readtrail) { va_list args; va_start(args, fmt); vprintf(fmt, args); va_end(args); return 1;#ifdef PRINTF va_list args; va_start(args, fmt); vprintf(fmt, args); va_end(args); return 1;extern void printm(int);#ifndef SC#define getframe(i) &trail[i];static long HHH, DDD, hiwater;static long CNT1, CNT2;static int stackwrite;static int stackread;static Trail frameptr;Trail *getframe(int d){ if (CNT1 == CNT2) return &trail[d]; if (d >= (CNT1-CNT2)*DDD) return &trail[d - (CNT1-CNT2)*DDD]; if (!stackread && (stackread = open(stackfile, 0)) < 0) { printf("getframe: cannot open %%s\n", stackfile); wrapup(); if (lseek(stackread, d* (off_t) sizeof(Trail), SEEK_SET) == -1 || read(stackread, &frameptr, sizeof(Trail)) != sizeof(Trail)) { printf("getframe: frame read error\n"); return &frameptr;#if !defined(SAFETY) && !defined(BITSTATE)#if !defined(FULLSTACK) || defined(MA)#define depth_of(x) A_depth /* an estimate */depth_of(struct H_el *s){ Trail *t; int d; for (d = 0; d <= A_depth; d++) { t = getframe(d); if (s == t->ostate) return d; printf("pan: cannot happen, depth_of\n"); return depthfound;voidpan_exit(int val){ if (signoff) printf("--end of output--\n"); exit(val);char *transmognify(char *s){ char *v, *w; static char buf[2][2048]; int i, toggle = 0; if (!s || strlen(s) > 2047) return s; memset(buf[0], 0, 2048); memset(buf[1], 0, 2048); strcpy(buf[toggle], s); while ((v = strstr(buf[toggle], "{c_code"))) { *v = '\0'; v++; strcpy(buf[1-toggle], buf[toggle]); for (w = v; *w != '}' && *w != '\0'; w++) /* skip */; if (*w != '}') return s; *w = '\0'; w++; for (i = 0; code_lookup[i].c; i++) if (strcmp(v, code_lookup[i].c) == 0 && strlen(v) == strlen(code_lookup[i].c)) { if (strlen(buf[1-toggle]) + strlen(code_lookup[i].t) + strlen(w) > 2047) return s; strcat(buf[1-toggle], code_lookup[i].t); break; } strcat(buf[1-toggle], w); toggle = 1 - toggle; buf[toggle][2047] = '\0'; return buf[toggle];char * transmognify(char *s) { return s; }add_src_txt(int ot, int tt){ Trans *t; char *q; for (t = trans[ot][tt]; t; t = t->nxt) { printf("\t\t"); q = transmognify(t->tp); for ( ; q && *q; q++) if (*q == '\n') printf("\\n"); else putchar(*q);wrap_trail(void){ static int wrap_in_progress = 0; int i; short II; P0 *z; if (wrap_in_progress++) return; printf("spin: trail ends after %%ld steps\n", depth); if (onlyproc >= 0) { if (onlyproc >= now._nr_pr) pan_exit(0); II = onlyproc; z = (P0 *)pptr(II); printf("%%3ld: proc %%d (%%s) ", depth, II, procname[z->_t]); for (i = 0; src_all[i].src; i++) if (src_all[i].tp == (int) z->_t) { printf(" line %%3d", src_all[i].src[z->_p]); printf(" (state %%2d)", z->_p); if (!stopstate[z->_t][z->_p]) printf(" (invalid end state)"); add_src_txt(z->_t, z->_p); pan_exit(0); printf("#processes %%d:\n", now._nr_pr); if (depth < 0) depth = 0; for (II = 0; II < now._nr_pr; II++) { z = (P0 *)pptr(II); c_globals(); c_locals(II, z->_t);#ifdef ON_EXIT ON_EXIT; pan_exit(0);FILE *findtrail(void){ FILE *fd; char fnm[512], *q; char MyFile[512]; strcpy(MyFile, TrailFile); if (whichtrail) { sprintf(fnm, "%%s%%d.%%s", MyFile, whichtrail, tprefix); fd = fopen(fnm, "r"); if (fd == NULL && (q = strchr(MyFile, '.'))) { *q = '\0'; sprintf(fnm, "%%s%%d.%%s", MyFile, whichtrail, tprefix); *q = '.'; fd = fopen(fnm, "r"); if (fd == NULL) { printf("pan: cannot find %%s%%d.%%s or %%s\n", MyFile, whichtrail, tprefix, fnm); pan_exit(1); } } { sprintf(fnm, "%%s.%%s", MyFile, tprefix); sprintf(fnm, "%%s.%%s", MyFile, tprefix); { printf("pan: cannot find %%s.%%s or %%s\n", MyFile, tprefix, fnm); } } } if (fd == NULL) { printf("pan: cannot find trailfile %%s\n", fnm); pan_exit(1); return fd;uchar do_transit(Trans *, short);getrail(void) int i, t_id, lastnever=-1; short II; Trans *t; fd = findtrail(); /* exits if unsuccessful */ while (fscanf(fd, "%%ld:%%d:%%d\n", &depth, &i, &t_id) == 3) { if (depth == -1) printf("<<<<>>>>\n"); if (depth < 0) continue; if (i > now._nr_pr) { printf("pan: Error, proc %%d invalid pid ", i); printf("transition %%d\n", t_id); break; } II = i; for (t = trans[z->_t][z->_p]; t; t = t->nxt) if (t->t_id == t_id) if (!t) { for (i = 0; i < NrStates[z->_t]; i++) { t = trans[z->_t][i]; if (t && t->t_id == t_id) { printf(" Recovered at state %%d\n", i); z->_p = i; goto recovered; } } printf("pan: Error, proc %%d type %%d state %%d: ", II, z->_t, z->_p); printf("transition %%d not found\n", t_id); for (t = trans[z->_t][z->_p]; t; t = t->nxt) printf(" t_id %%d -- case %%d, [%%s]\n", t->t_id, t->forw, t->tp); break; /* pan_exit(1); */recovered: if (gui) simvals[0] = '\0'; this = pptr(II); trpt->tau |= 1; if (!do_transit(t, II)) { if (onlyproc >= 0 && II != onlyproc) goto moveon; printf("pan: error, next transition UNEXECUTABLE on replay\n"); printf(" most likely causes: missing c_track statements\n"); printf(" or illegal side-effects in c_expr statements\n"); if (onlyproc >= 0 && II != onlyproc) goto moveon; if (verbose) { printf("depth: %%3ld proc: %%3d trans: %%3d (%%d procs) ", depth, II, t_id, now._nr_pr); printf("forw=%%3d [%%s]\n", t->forw, q); c_globals(); for (i = 0; i < now._nr_pr; i++) { c_locals(i, ((P0 *)pptr(i))->_t); } else if (strcmp(procname[z->_t], ":never:") == 0) { if (lastnever != (int) z->_p) { for (i = 0; src_all[i].src; i++) if (src_all[i].tp == (int) z->_t) { printf("MSC: ~G %%d\n", src_all[i].src[z->_p]); break; } if (!src_all[i].src) printf("MSC: ~R %%d\n", z->_p); lastnever = z->_p; goto sameas; if (strcmp(procname[z->_t], ":np_:") != 0) {sameas: if (no_rck) goto moveon; if (coltrace) { printf("%%ld: ", depth); for (i = 0; i < II; i++) printf("\t\t"); printf("%%s(%%d):", procname[z->_t], II); printf("[%%s]\n", q?q:""); } else if (!silent) { if (strlen(simvals) > 0) { printf("%%3ld: proc %%2d (%%s)", depth, II, procname[z->_t]); for (i = 0; src_all[i].src; i++) { printf(" line %%3d \"pan_in\" ", printf("(state %%d) [values: %%s]\n", z->_p, simvals); } printf("(state %%d) [%%s]\n", z->_p, q?q:""); printf("\n");moveon: z->_p = t->st; wrap_trail();f_pid(int pt){ int i; for (i = 0; i < now._nr_pr; i++) { z = (P0 *)pptr(i); if (z->_t == (unsigned) pt) return BASE+z->_pid; return -1;void check_claim(int);bstore_mod(char *v, int n) /* hasharray size not a power of two */{ unsigned long x, y; unsigned int i = 1; d_hash((uchar *) v, n); /* sets j3, j4, K1, K2 */ x = K2; y = j3; for (;;) { if (!(SS[x%%udmem]&(1< RANDSTOR) return 0; { SS[x%%udmem] |= (1< 0) sprintf(fnm, "%%s%%d.%%s", MyFile, Nr_Trails-1, tprefix); else sprintf(fnm, "%%s.%%s", MyFile, tprefix); if ((fd = creat(fnm, TMODE)) < 0) { if ((q = strchr(MyFile, '.'))) if (iterative == 0 && Nr_Trails-1 > 0) sprintf(fnm, "%%s%%d.%%s", MyFile, Nr_Trails-1, tprefix); sprintf(fnm, "%%s.%%s", MyFile, tprefix); fd = creat(fnm, TMODE); } } if (fd < 0) { printf("pan: cannot create %%s\n", fnm); perror("cause"); { printf("pan: wrote %%s\n", fnm);#ifdef BFS#define Q_PROVISO#ifndef INLINE_REV#define INLINE_REVtypedef struct SV_Hold { State *sv; int sz; struct SV_Hold *nxt;} SV_Hold;typedef struct EV_Hold { char *sv; int nrpr; int nrqs;#if VECTORSZ>32000 int *po; short *po; int *qo; uchar *ps, *qs; struct EV_Hold *nxt;} EV_Hold;typedef struct BFS_Trail { Trail *frame; SV_Hold *onow; EV_Hold *omask;#ifdef Q_PROVISO struct H_el *lstate; short boq; struct BFS_Trail *nxt;} BFS_Trail;BFS_Trail *bfs_trail, *bfs_bot, *bfs_free;SV_Hold *svhold, *svfree;uchar do_reverse(Trans *, short, uchar);void snapshot(void);SV_Hold *getsv(int n){ SV_Hold *h = (SV_Hold *) 0, *oh; oh = (SV_Hold *) 0; for (h = svfree; h; oh = h, h = h->nxt) { if (n == h->sz) { if (!oh) svfree = h->nxt; oh->nxt = h->nxt; h->nxt = (SV_Hold *) 0; if (n < h->sz) { h = (SV_Hold *) 0; /* else continue */ if (!h) { h = (SV_Hold *) emalloc(sizeof(SV_Hold)); h->sz = n; h->sv = (State *) emalloc(sizeof(State) - VECTORSZ + n); return h;EV_Hold *getsv_mask(int n){ EV_Hold *h; static EV_Hold *kept = (EV_Hold *) 0; for (h = kept; h; h = h->nxt) if (n == h->sz && (memcmp((char *) Mask, (char *) h->sv, n) == 0) && (now._nr_pr == h->nrpr) && (now._nr_qs == h->nrqs) && (memcmp((char *) proc_offset, (char *) h->po, now._nr_pr * sizeof(int)) == 0) && (memcmp((char *) q_offset, (char *) h->qo, now._nr_qs * sizeof(int)) == 0) && (memcmp((char *) proc_offset, (char *) h->po, now._nr_pr * sizeof(short)) == 0) && (memcmp((char *) q_offset, (char *) h->qo, now._nr_qs * sizeof(short)) == 0) && (memcmp((char *) proc_skip, (char *) h->ps, now._nr_pr * sizeof(uchar)) == 0) && (memcmp((char *) q_skip, (char *) h->qs, now._nr_qs * sizeof(uchar)) == 0)) { h = (EV_Hold *) emalloc(sizeof(EV_Hold)); h->nrpr = now._nr_pr; h->nrqs = now._nr_qs; h->sv = (char *) emalloc(n * sizeof(char)); memcpy((char *) h->sv, (char *) Mask, n); if (now._nr_pr > 0) { h->po = (int *) emalloc(now._nr_pr * sizeof(int)); h->ps = (int *) emalloc(now._nr_pr * sizeof(int)); memcpy((char *) h->po, (char *) proc_offset, now._nr_pr * sizeof(int)); memcpy((char *) h->po, (char *) proc_offset, now._nr_pr * sizeof(short)); memcpy((char *) h->ps, (char *) proc_skip, now._nr_pr * sizeof(uchar)); if (now._nr_qs > 0) { h->qo = (int *) emalloc(now._nr_qs * sizeof(int)); h->qs = (int *) emalloc(now._nr_qs * sizeof(int)); memcpy((char *) h->qo, (char *) q_offset, now._nr_qs * sizeof(int)); memcpy((char *) h->qo, (char *) q_offset, now._nr_qs * sizeof(short)); memcpy((char *) h->qs, (char *) q_skip, now._nr_qs * sizeof(uchar)); h->nxt = kept; kept = h;freesv(SV_Hold *p){ SV_Hold *h, *oh; if (h->sz >= p->sz) if (!oh) { p->nxt = svfree; svfree = p; { p->nxt = h; oh->nxt = p;BFS_Trail *get_bfs_frame(void){ BFS_Trail *t; if (bfs_free) { t = bfs_free; bfs_free = bfs_free->nxt; t->nxt = (BFS_Trail *) 0; { t = (BFS_Trail *) emalloc(sizeof(BFS_Trail)); t->frame = (Trail *) emalloc(sizeof(Trail)); return t;push_bfs(Trail *f, int d) t = get_bfs_frame(); memcpy((char *)t->frame, (char *)f, sizeof(Trail)); t->frame->o_tt = d; /* depth */ t->boq = boq; t->onow = getsv(vsize); memcpy((char *)t->onow->sv, (char *)&now, vsize); t->omask = getsv_mask(vsize);#if defined(FULLSTACK) && defined(Q_PROVISO) t->lstate = Lstate; if (!bfs_bot) { bfs_bot = bfs_trail = t; { bfs_bot->nxt = t; bfs_bot = t;#ifdef CHECK printf("PUSH %%u (%%d)\n", t->frame, d);pop_bfs(void) if (!bfs_trail) return (Trail *) 0; t = bfs_trail; bfs_trail = t->nxt; bfs_bot = (BFS_Trail *) 0;#if defined(Q_PROVISO) && !defined(BITSTATE) && !defined(NOREDUCE) if (t->lstate) t->lstate->tagged = 0; t->nxt = bfs_free; bfs_free = t; vsize = t->onow->sz; boq = t->boq; memcpy((uchar *) &now, (uchar *) t->onow->sv, vsize); memcpy((uchar *) Mask, (uchar *) t->omask->sv, vsize); if (now._nr_pr > 0) { memcpy((char *)proc_offset, (char *)t->omask->po, now._nr_pr * sizeof(int)); { memcpy((char *)proc_offset, (char *)t->omask->po, now._nr_pr * sizeof(short)); memcpy((char *)proc_skip, (char *)t->omask->ps, now._nr_pr * sizeof(uchar)); if (now._nr_qs > 0) { memcpy((uchar *)q_offset, (uchar *)t->omask->qo, now._nr_qs * sizeof(int)); { memcpy((uchar *)q_offset, (uchar *)t->omask->qo, now._nr_qs * sizeof(short)); memcpy((uchar *)q_skip, (uchar *)t->omask->qs, now._nr_qs * sizeof(uchar)); freesv(t->onow); /* omask not freed */ printf("POP %%u (%%d)\n", t->frame, t->frame->o_tt); return t->frame;store_state(Trail *ntrpt, int shortcut, short oboq) Trans *t2 = (Trans *) 0; uchar ot; int tt, E_state; uchar o_opm = trpt->o_pm, *othis = this; if (shortcut) {#ifdef VERBOSE printf("claim: shortcut\n"); goto store_it; /* no claim move */ this = (((uchar *)&now)+proc_offset[0]); /* 0 = never claim */ trpt->o_pm = 0; tt = (int) ((P0 *)this)->_p; ot = (uchar) ((P0 *)this)->_t;#ifdef HAS_UNLESS E_state = 0; for (t2 = trans[ot][tt]; t2; t2 = t2?t2->nxt:(Trans *)0) if (E_state > 0 && E_state != t2->e_trans) if (do_transit(t2, 0)) if (!reached[ot][t2->st]) printf("depth: %%d -- claim move from %%d -> %%d\n", trpt->o_tt, ((P0 *)this)->_p, t2->st); E_state = t2->e_trans; if (t2->st > 0) { ((P0 *)this)->_p = t2->st; reached[ot][t2->st] = 1;#ifndef NOCLAIM check_claim(t2->st); if (now._nr_pr == 0) /* claim terminated */ uerror("end state in claim reached");#ifdef PEG peg[t2->forw]++; trpt->o_pm |= 1; if (t2->atom&2) Uerror("atomic in claim not supported in BFS mode");store_it: if (!bstore((char *)&now, vsize))#ifdef MA if (!gstore((char *)&now, vsize, 0)) if (!hstore((char *)&now, vsize)) { nstates++;#ifndef NOREDUCE trpt->tau |= 64;#if SYNC if (boq != -1) midrv++; else if (oboq != -1) { Trail *x; x = (Trail *) trpt->ostate; /* pre-rv state */ if (x) x->o_pm |= 4; /* mark success */ push_bfs(ntrpt, trpt->o_tt+1); } else { truncs++;#if !defined(NOREDUCE) && defined(FULLSTACK) && defined(Q_PROVISO)#if !defined(QLIST) && !defined(BITSTATE) if (Lstate && Lstate->tagged) trpt->tau |= 64; if (trpt->tau&32) { BFS_Trail *tprov; for (tprov = bfs_trail; tprov; tprov = tprov->nxt) if (!memcmp((uchar *)&now, (uchar *)tprov->onow->sv, vsize)) { trpt->tau |= 64; break; /* state is in queue */ } } ((P0 *)this)->_p = tt; /* reset claim */ if (t2) do_reverse(t2, 0, 0); this = othis; trpt->o_pm = o_opm;Trail *ntrpt;bfs(void){ Trans *t; Trail *otrpt, *x; uchar _n, _m, ot, nps = 0; int tt, E_state; short II, From = (short) (now._nr_pr-1), To = BASE; short oboq = boq; ntrpt = (Trail *) emalloc(sizeof(Trail)); trpt->ostate = (struct H_el *) 0; trpt->tau = 0; trpt->o_tt = -1; store_state(ntrpt, 0, oboq); /* initial state */ while ((otrpt = pop_bfs())) /* also restores now */ { memcpy((char *) trpt, (char *) otrpt, sizeof(Trail));#if defined(C_States) && (HAS_TRACK==1) c_revert((uchar *) &(now.c_state[0])); if (trpt->o_pm & 4) printf("Revisit of atomic not needed (%%d)\n", trpt->o_pm); nps = 0; if (trpt->o_pm == 8) { revrv++; if (trpt->tau&8) { printf("Break atomic (pm:%%d,tau:%%d)\n", trpt->o_pm, trpt->tau); trpt->tau &= ~8; else if (trpt->tau&32) printf("Void preselection (pm:%%d,tau:%%d)\n", trpt->tau &= ~32; nps = 1; /* no preselection in repeat */ trpt->o_pm &= ~(4|8); if (trpt->o_tt > mreached) { mreached = trpt->o_tt; if (mreached%%10 == 0) { printf("Depth= %%7d States= %%7g ", mreached, nstates); printf("Transitions= %%7g ", nstates+truncs); printf("Nodes= %%7d ", nr_states); printf("Memory= %%-6.3f\n", memcnt/1000000.); fflush(stdout); depth = trpt->o_tt; if (depth >= maxdepth) Trail *x; if (boq != -1) { x = (Trail *) trpt->ostate; if (x) x->o_pm |= 4; /* not failing */ truncs++; if (!warned) { warned = 1; printf("error: max search depth too small\n"); if (bounded) uerror("depth limit reached"); if (boq == -1 && !(trpt->tau&8) && nps == 0) for (II = now._nr_pr-1; II >= BASE; II -= 1)Pickup: this = pptr(II); tt = (int) ((P0 *)this)->_p; ot = (uchar) ((P0 *)this)->_t; if (trans[ot][tt]->atom & 8) { t = trans[ot][tt]; if (t->qu[0] != 0) { Ccheck++; if (!q_cond(II, t)) continue; Cholds++; From = To = II; trpt->tau |= 32; /* preselect marker */ printf("%%3d: proc %%d PreSelected (tau=%%d)\n", depth, II, trpt->tau); goto MainLoop; trpt->tau &= ~32;Repeat: if (trpt->tau&8) /* atomic */ { From = To = (short ) trpt->pr; nlinks++; { From = now._nr_pr-1; To = BASE;MainLoop: _n = _m = 0; for (II = From; II >= To; II -= 1) this = (((uchar *)&now)+proc_offset[II]); /* no rendezvous with same proc */ if (boq != -1 && trpt->pr == II) continue; ntrpt->pr = (uchar) II; ntrpt->st = tt; trpt->o_pm &= ~1; /* no move yet */ trpt->o_event = now._event; if (!provided(II, ot, tt, t)) continue; E_state = 0; for (t = trans[ot][tt]; t; t = t->nxt) if (E_state > 0 && E_state != t->e_trans) break; ntrpt->o_t = t; oboq = boq; if (!(_m = do_transit(t, II))) continue; trpt->o_pm |= 1; /* we moved */ (trpt+1)->o_m = _m; /* for unsend */ peg[t->forw]++; printf("%%3d: proc %%d exec %%d, ", depth, II, t->forw); printf("%%d to %%d, %%s %%s %%s", tt, t->st, t->tp, (t->atom&2)?"atomic":"", (boq != -1)?"rendez-vous":""); if (t->e_trans) printf(" (escapes to state %%d)", t->st); printf(" %%saccepting [tau=%%d]\n", (trpt->o_pm&2)?"":"non-", trpt->tau); E_state = t->e_trans;#if SYNC>0 if (t->e_trans > 0 && (boq != -1 /* || oboq != -1 */)) { fprintf(efd, "error: the use of rendezvous stmnt in the escape clause\n"); fprintf(efd, " of an unless stmnt is not compatible with -DBFS\n"); pan_exit(1); if (t->st > 0) ((P0 *)this)->_p = t->st; /* ptr to pred: */ ntrpt->ostate = (struct H_el *) otrpt; ntrpt->st = tt; if (boq == -1 && (t->atom&2)) /* atomic */ ntrpt->tau = 8; /* record for next move */ else ntrpt->tau = 0; store_state(ntrpt, (boq != -1 || (t->atom&2)), oboq); now._event = trpt->o_event; /* undo move and continue */ trpt++; /* this is where ovals and ipt are set */ do_reverse(t, II, _m); /* restore now. */ trpt--; printf("%%3d: proc %%d ", depth, II); printf("reverses %%d, %%d to %%d,", t->forw, tt, t->st); printf(" %%s [abit=%%d,adepth=%%d,", t->tp, now._a_t, A_depth); printf("tau=%%d,%%d]\n", trpt->tau, (trpt-1)->tau); reached[ot][t->st] = 1; reached[ot][tt] = 1; ((P0 *)this)->_p = tt; _n |= _m; /* preselected - no succ definitely outside stack */ if ((trpt->tau&32) && !(trpt->tau&64)) { From = now._nr_pr-1; To = BASE; printf("%%3d: proc %%d UnSelected (_n=%%d, tau=%%d)\n", depth, II+1, (int) _n, trpt->tau); _n = 0; trpt->tau &= ~32; if (II >= BASE) goto Pickup; goto MainLoop; trpt->tau &= ~(32|64); if (_n != 0) printf("%%3d: no move [II=%%d, tau=%%d, boq=%%d, _nr_pr=%%d]\n", depth, II, trpt->tau, boq, now._nr_pr); if (boq != -1) { failedrv++; x = (Trail *) trpt->ostate; /* pre-rv state */ if (!x) continue; /* root state */ if ((x->tau&8) || (x->tau&32)) /* break atomic or preselect at parent */ { x->o_pm |= 8; /* mark failure */ this = (((uchar *)&now)+proc_offset[otrpt->pr]); printf("\treset state of %%d from %%d to %%d\n", otrpt->pr, ((P0 *)this)->_p, otrpt->st); ((P0 *)this)->_p = otrpt->st; unsend(boq); /* retract rv offer */ boq = -1; push_bfs(x, x->o_tt); printf("failed rv, repush with %%d\n", x->o_pm); else printf("failed rv, tau at parent: %%d\n", x->tau); } else if (now._nr_pr > 0) if ((trpt->tau&8)) /* atomic */ { trpt->tau &= ~(1|8); /* 1=timeout, 8=atomic */ printf("%%3d: atomic step proc %%d blocks\n", depth, II+1); goto Repeat; if (!(trpt->tau&1)) /* didn't try timeout yet */ { trpt->tau |= 1; printf("%%d: timeout\n", depth);#ifndef VERI if (!noends && !a_cycles && !endstate()) uerror("invalid end state");putter(Trail *trpt, int fd){ long j; if (!trpt) return; if (trpt != (Trail *) trpt->ostate) putter((Trail *) trpt->ostate, fd); if (trpt->o_t) { sprintf(snap, "%%d:%%d:%%d\n", trcnt++, trpt->pr, trpt->o_t->t_id); j = strlen(snap); if (write(fd, snap, j) != j) { printf("pan: error writing %%s\n", fnm); pan_exit(1);nuerror(char *str){ int fd = make_trail(); int j; if (fd < 0) return; sprintf(snap, "-2:%%d:-2\n", VERI); write(fd, snap, strlen(snap));#ifdef MERGED sprintf(snap, "-4:-4:-4\n"); trcnt = 1; putter(trpt, fd); if (ntrpt->o_t) trcnt++, ntrpt->pr, ntrpt->o_t->t_id); close(fd); if (errors >= upto && upto != 0)do_the_search(void) depth = mreached = 0; trpt = &trail[0]; trpt->tau |= 4; /* the claim moves first */ for (i = 0; i < (int) now._nr_pr; i++) { P0 *ptr = (P0 *) pptr(i);#ifndef NP if (!(trpt->o_pm&2) && accpstate[ptr->_t][ptr->_p]) { trpt->o_pm |= 2; if (!(trpt->o_pm&4) && progstate[ptr->_t][ptr->_p]) { trpt->o_pm |= 4; if (accpstate[EVENT_TRACE][now._event]) { trpt->o_pm |= 2; if (progstate[EVENT_TRACE][now._event]) { trpt->o_pm |= 4;#ifndef NOCOMP Mask[0] = Mask[1] = 1; /* _nr_pr, _nr_qs */ if (!a_cycles) { i = &(now._a_t) - (uchar *) &now; Mask[i] = 1; /* _a_t */#ifndef NOFAIR if (!fairness) { int j = 0; i = &(now._cnt[0]) - (uchar *) &now; while (j++ < NFAIR) Mask[i++] = 1; /* _cnt[] */ if (fairness && (a_cycles && (trpt->o_pm&2))) { now._a_t = 2; /* set the A-bit */ now._cnt[0] = now._nr_pr + 1; printf("%%3d: fairness Rule 1, cnt=%%d, _a_t=%%d\n", depth, now._cnt[now._a_t&1], now._a_t); /* capture initial state of tracked C objects */ c_update((uchar *) &(now.c_state[0])); if (readtrail) getrail(); /* no return */ bfs();#if defined(C_States) && defined(HAS_STACK) && (HAS_TRACK==1) /* initial state of tracked & unmatched objects */ c_stack((uchar *) &(svtack->c_stack[0]));#ifdef RANDOMIZE srand(123); new_state(); /* start 1st DFS */#ifdef INLINE_REVuchardo_reverse(Trans *t, short II, uchar M){ uchar _m = M; int tt = (int) ((P0 *)this)->_p;#include REVERSE_MOVESR999: return _m;#ifndef INLINEstatic char _tp = 'n'; static int _qid = 0;do_transit(Trans *t, short II){ uchar _m = 0;#ifdef M_LOSS uchar delta_m = 0; uchar ot = (uchar) ((P0 *)this)->_t; if (ot == EVENT_TRACE) boq = -1;#define continue { boq = oboq; return 0; }#define continue return 0#ifdef SEPARATE#include FORWARD_MOVESP999: if (ot == EVENT_TRACE) boq = oboq; return _m;#undef continuerequire(char tp, int qid) _tp = tp; _qid = qid; if (now._event != endevent) for (t = trans[EVENT_TRACE][now._event]; t; t = t->nxt) { if (do_transit(t, EVENT_TRACE)) { now._event = t->st; reached[EVENT_TRACE][t->st] = 1; printf(" event_trace move to -> %%d\n", t->st);#ifndef BFS if (accpstate[EVENT_TRACE][now._event]) (trpt+1)->o_pm |= 2; if (progstate[EVENT_TRACE][now._event]) (trpt+1)->o_pm |= 4;#ifdef NEGATED_TRACE if (now._event == endevent) depth++; trpt++; uerror("event_trace error (all events matched)"); trpt--; depth--; for (t = t->nxt; t; t = t->nxt) { if (do_transit(t, EVENT_TRACE)) Uerror("non-determinism in event-trace"); return; else printf(" event_trace miss '%%c' -- %%d, %%d, %%d\n", tp, qid, now._event, t->forw); now._event = endevent; /* only 1st try will count -- fixed 4.2.6 */ depth++; trpt++; uerror("event_trace error (no matching event)"); trpt--; depth--;enabled(int iam, int pid){ Trans *t; uchar *othis = this; int res = 0; int tt; uchar ot; /* if (pid > 0) */ pid++; if (pid == iam) Uerror("used: enabled(pid=thisproc)"); if (pid < 0 || pid >= (int) now._nr_pr) return 0; this = pptr(pid); TstOnly = 1; tt = (int) ((P0 *)this)->_p; ot = (uchar) ((P0 *)this)->_t; if (do_transit(t, (short) pid)) { res = 1; TstOnly = 0; return res;snapshot(void){ static long sdone = (long) 0; long ndone = (unsigned long) nstates/1000000; if (ndone == sdone) return; sdone = ndone; printf("Depth= %%7d States= %%7g ", mreached, nstates); printf("Transitions= %%7g ", nstates+truncs); printf("Nodes= %%7d ", nr_states); printf("Memory= %%-6.3f\n", memcnt/1000000.); fflush(stdout);#ifdef SCstack2disk(void) if (!stackwrite && (stackwrite = creat(stackfile, TMODE)) < 0) Uerror("cannot create stackfile"); if (write(stackwrite, trail, DDD*sizeof(Trail)) != DDD*sizeof(Trail)) Uerror("stackfile write error -- disk is full?"); memmove(trail, &trail[DDD], (HHH-DDD+2)*sizeof(Trail)); memset(&trail[HHH-DDD+2], 0, (omaxdepth - HHH + DDD - 2)*sizeof(Trail)); CNT1++;disk2stack(void){ long have; CNT2++; memmove(&trail[DDD], trail, (HHH-DDD+2)*sizeof(Trail)); || lseek(stackwrite, -DDD* (off_t) sizeof(Trail), SEEK_CUR) == -1) Uerror("disk2stack lseek error"); Uerror("cannot open stackfile"); if (lseek(stackread, (CNT1-CNT2)*DDD* (off_t) sizeof(Trail), SEEK_SET) == -1) have = read(stackread, trail, DDD*sizeof(Trail)); if (have != DDD*sizeof(Trail)) Uerror("stackfile read error");uchar *Pptr(int x){ if (x < 0 || x >= MAXPROC || !proc_offset[x]) return noptr; return (uchar *) pptr(x);int qs_empty(void);/* * new_state() is the main DFS search routine in the verifier * it has a lot of code ifdef-ed together to support * different search modes, which makes it quite unreadable. * if you are studying the code, first use the C preprocessor * to generate a specific version from the pan.c source, * e.g. by saying: * gcc -E -DNOREDUCE -DBITSTATE pan.c > ppan.c * and then study the resulting file, rather than this one */#if !defined(BFS) && (!defined(BITSTATE) || !defined(MA))new_state(void) uchar _n, _m, ot; short ooi, eoi; short II, JJ = 0, kk; int tt; short From = now._nr_pr-1, To = BASE;Down: printf("%%d: Down - %%s", depth, (trpt->tau&4)?"claim":"program"); printf(" %%saccepting [pids %%d-%%d]\n", (trpt->o_pm&2)?"":"non-", From, To); if (depth > hiwater) { stack2disk(); maxdepth += DDD; hiwater += DDD; trpt -= DDD; if(verbose) printf("zap %%d: %%d (maxdepth now %%d)\n", CNT1, hiwater, maxdepth); trpt->tau &= ~(16|32|64); /* make sure these are off */#if defined(FULLSTACK) && defined(MA) trpt->proviso = 0; if (depth >= maxdepth) { truncs++; (trpt+1)->o_n = 1; /* not a deadlock */ if (!warned) { warned = 1; printf("error: max search depth too small\n"); if (bounded) uerror("depth limit reached"); (trpt-1)->tau |= 16; /* worstcase guess */ goto Up;AllOver:#if defined(FULLSTACK) && !defined(MA) /* if atomic or rv move, carry forward previous state */ trpt->ostate = (trpt-1)->ostate; if ((trpt->tau&4) || ((trpt-1)->tau&128)) if (boq == -1) { /* if not mid-rv */#ifndef SAFETY /* this check should now be redundant * because the seed state also appears * on the 1st dfs stack and would be * matched in hstore below */ if ((now._a_t&1) && depth > A_depth) { if (!memcmp((char *)&A_Root, (char *)&now, vsize)) depthfound = A_depth; printf("matches seed\n");#ifdef NP uerror("non-progress cycle"); uerror("acceptance cycle"); goto Up; printf("not seed\n"); if (!(trpt->tau&8)) /* if no atomic move */#ifdef CNTRSTACK II = bstore((char *)&now, vsize); trpt->j6 = j1; trpt->j7 = j2; JJ = LL[j1] && LL[j2];#ifdef FULLSTACK JJ = onstack_now(); JJ = II; /* worstcase guess for p.o. */ II = gstore((char *)&now, vsize, 0);#ifndef FULLSTACK JJ = II; JJ = (II == 2)?1:0; II = hstore((char *)&now, vsize); kk = (II == 1 || II == 2); if (!fairness && a_cycles) if (II == 2 && ((trpt->o_pm&2) || ((trpt-1)->o_pm&2))) { II = 3; /* Schwoon & Esparza 2005, Gastin&Moro 2004 */ printf("state match on dfs stack\n"); goto same_case; if (!JJ && (now._a_t&1) && depth > A_depth) { int oj1 = j1; uchar o_a_t = now._a_t; now._a_t &= ~(1|16|32); if (onstack_now()) { II = 3; printf("state match on 1st dfs stack\n"); now._a_t = o_a_t; j1 = oj1; if (II == 3 && a_cycles && (now._a_t&1)) if (fairness && now._cnt[1] > 1) /* was != 0 */ { printf(" fairness count non-zero\n"); II = 0; } else#ifndef BITSTATE nShadow--;same_case: if (Lstate) depthfound = Lstate->D; uerror("non-progress cycle"); uerror("acceptance cycle"); goto Up; } if ((II && JJ) || (II == 3)) { /* marker for liveness proviso */ (trpt-1)->tau |= 16; truncs2++; if (!II || !JJ) { /* successor outside stack */ (trpt-1)->tau |= 64; if (II) if (!kk) if ((unsigned long) nstates%%1000000 == 0) snapshot(); if (vprefix > 0) if (write(svfd, (uchar *) &now, vprefix) != vprefix) { fprintf(efd, "writing %%s.svd failed\n", Source); wrapup();#if defined(MA) && defined(W_XPT) if ((unsigned long) nstates%%W_XPT == 0) { void w_xpoint(void); w_xpoint();#if defined(FULLSTACK) || defined(CNTRSTACK) onstack_put();#ifdef DEBUG2 printf("%%d: putting %%u (%%d)\n", depth, trpt->ostate, (trpt->ostate)?trpt->ostate->tagged:0); printf("%%d: putting\n", depth); if (depth > mreached) mreached = depth; if (trpt->tau&4) trpt->tau &= ~(1|2); /* timeout and -request off */ _n = 0; (trpt+1)->o_n = 0; if (now._nr_pr == 0) /* claim terminated */ uerror("end state in claim reached"); check_claim(((P0 *)pptr(0))->_p);Stutter: if (trpt->tau&4) /* must make a claimmove */ if ((now._a_t&2) /* A-bit set */ && now._cnt[now._a_t&1] == 1) { now._a_t &= ~2; now._cnt[now._a_t&1] = 0; trpt->o_pm |= 16; printf("%%3d: fairness Rule 3.: _a_t = %%d\n", depth, now._a_t); II = 0; /* never */ goto Veri0; /* Look for a process with only safe transitions */ /* (special rules apply in the 2nd dfs) */#ifdef SAFETY if (boq == -1 && From != To)/* implied: #ifdef FULLSTACK */ if (boq == -1 && From != To && (!(now._a_t&1) || (a_cycles && !((trpt-1)->proviso)) !(trpt->proviso)) (trpt-1)->ostate && !(((char *)&((trpt-1)->ostate->state))[0] & 128)) !(((char *)&(trpt->ostate->state))[0] & 128)) (trpt-1)->ostate && (trpt-1)->ostate->proviso == 0) trpt->ostate->proviso == 0) ))/* #endif */ for (II = From; II >= To; II -= 1)Resume: /* pick up here if preselect fails */ tt = (int) ((P0 *)this)->_p; ot = (uchar) ((P0 *)this)->_t; if (trans[ot][tt]->atom & 8) { t = trans[ot][tt]; if (t->qu[0] != 0) { Ccheck++; if (!q_cond(II, t)) Cholds++; From = To = II;#ifdef NIBIS t->om = 0; trpt->tau |= 32; /* preselect marker */ printf("%%3d: proc %%d Pre", depth, II); printf("Selected (om=%%d, tau=%%d)\n", t->om, trpt->tau); printf("%%3d: proc %%d PreSelected (tau=%%d)\n", depth, II, trpt->tau); goto Again; trpt->tau &= ~32;#if !defined(NOREDUCE) || (defined(ETIM) && !defined(VERI))Again: /* The Main Expansion Loop over Processes */ trpt->o_pm &= ~(8|16|32|64); /* fairness-marks */ if (fairness && boq == -1 && (!(trpt->tau&4) && !((trpt-1)->tau&128)) && !(trpt->tau&8)) { /* A_bit = 1; Cnt = N in acc states with A_bit 0 */ if (!(now._a_t&2)) if (a_cycles && (trpt->o_pm&2)) { /* Accepting state */ now._a_t |= 2; now._cnt[now._a_t&1] = now._nr_pr + 1; trpt->o_pm |= 8; printf("%%3d: fairness Rule 1: cnt=%%d, _a_t=%%d\n", depth, now._cnt[now._a_t&1], now._a_t); { /* A_bit = 0 when Cnt 0 */ if (now._cnt[now._a_t&1] == 1) { now._a_t &= ~2; now._cnt[now._a_t&1] = 0; trpt->o_pm |= 16; printf("%%3d: fairness Rule 3: _a_t = %%d\n", /* no rendezvous with same proc */ if (boq != -1 && trpt->pr == II) continue;Veri0: /* don't repeat a previous preselected expansion */ /* could hit this if reduction proviso was false */ t = trans[ot][tt]; if (!(trpt->tau&4) && !(trpt->tau&1) && !(trpt->tau&32) && (t->atom & 8) && boq == -1 && From != To) { if (t->qu[0] == 0 || q_cond(II, t)) { _m = t->om; if (_m>_n||(_n>3&&_m!=0)) _n=_m; continue; /* did it before */ trpt->o_pm &= ~1; /* no move in this pid yet */ (trpt+1)->o_event = now._event; /* Fairness: Cnt++ when Cnt == II */ trpt->o_pm &= ~64; /* didn't apply rule 2 */ if (fairness && !(trpt->o_pm&32) && (now._a_t&2) && now._cnt[now._a_t&1] == II+2) { now._cnt[now._a_t&1] -= 1; /* claim need not participate */ if (II == 1) now._cnt[now._a_t&1] = 1; printf("%%3d: proc %%d fairness ", depth, II); printf("Rule 2: --cnt to %%d (%%d)\n", now._cnt[now._a_t&1], now._a_t); trpt->o_pm |= (32|64); if (!provided(II, ot, tt, t)) continue; /* check all trans of proc II - escapes first */ trpt->e_state = 0; (trpt+1)->pr = (uchar) II; (trpt+1)->st = tt; for (ooi = eoi = 0, t = trans[ot][tt]; t; t = t->nxt, ooi++) if (strcmp(t->tp, "else") == 0) eoi++; if (eoi) printf("randomizer: suppressed, saw else\n"); { eoi = rand()%%ooi; printf("randomizer: skip %%d in %%d\n", eoi, ooi); if (eoi-- <= 0) break;DOMORE: for ( ; t && ooi > 0; t = t->nxt, ooi--) for (t = trans[ot][tt]; t; t = t->nxt) /* exploring all transitions from * a single escape state suffices */ if (trpt->e_state > 0 && trpt->e_state != t->e_trans) printf("skip 2nd escape %%d (did %%d before)\n", t->e_trans, trpt->e_state); (trpt+1)->o_t = t;#ifdef INLINEP999: /* jumps here when move succeeds */ if (!(_m = do_transit(t, II))) continue; if (boq == -1)#ifdef CTL /* for branching-time, can accept reduction only if */ /* the persistent set contains just 1 transition */ { if ((trpt->tau&32) && (trpt->o_pm&1)) trpt->tau |= 16; trpt->o_pm |= 1; /* we moved */ peg[t->forw]++;#if defined(VERBOSE) || defined(CHECK)#if defined(SVDUMP) printf("%%3d: proc %%d exec %%d \n", depth, II, t->t_id); printf("%%3d: proc %%d exec %%d, ", depth, II, t->forw); printf("%%d to %%d, %%s %%s %%s", tt, t->st, t->tp, (t->atom&2)?"atomic":"", (boq != -1)?"rendez-vous":""); if (t->e_trans) printf(" (escapes to state %%d)", t->st); printf(" %%saccepting [tau=%%d]\n", (trpt->o_pm&2)?"":"non-", trpt->tau); printf(" randomizer %%d\n", ooi);#ifdef HAS_LAST if (II != 0) now._last = II - BASE; trpt->e_state = t->e_trans; depth++; trpt++; trpt->pr = (uchar) II; trpt->st = tt; trpt->o_pm &= ~(2|4); if (t->st > 0) { ((P0 *)this)->_p = t->st;/* moved down reached[ot][t->st] = 1; */ if (a_cycles)#if (ACCEPT_LAB>0 && !defined(NP)) || (PROG_LAB>0 && defined(HAS_NP)) int ii;#define P__Q ((P0 *)pptr(ii))#if ACCEPT_LAB>0 /* state 1 of np_ claim is accepting */ if (((P0 *)pptr(0))->_p == 1) trpt->o_pm |= 2; for (ii = 0; ii < (int) now._nr_pr; ii++) { if (accpstate[P__Q->_t][P__Q->_p]) { trpt->o_pm |= 2; } }#if defined(HAS_NP) && PROG_LAB>0 { if (progstate[P__Q->_t][P__Q->_p]) { trpt->o_pm |= 4;#undef P__Q trpt->o_t = t; trpt->o_n = _n; trpt->o_ot = ot; trpt->o_tt = tt; trpt->o_To = To; trpt->o_m = _m; trpt->tau = 0; trpt->oo_i = ooi; if (boq != -1 || (t->atom&2)) { trpt->tau |= 8; /* atomic sequence in claim */ if((trpt-1)->tau&4) trpt->tau |= 4; trpt->tau &= ~4; { if ((trpt-1)->tau&4) /* if claim allowed timeout, so */ /* does the next program-step: */ if (((trpt-1)->tau&1) && !(trpt->tau&4)) trpt->tau |= 1; if (boq == -1 && (t->atom&2)) { From = To = II; nlinks++; { From = now._nr_pr-1; To = BASE; goto Down; /* pseudo-recursion */Up: printf("%%d: Up - %%s\n", depth, (trpt->tau&4)?"claim":"program"); if (depth <= 0) return; /* e.g., if first state is old, after a restart */ if (CNT1 > CNT2 && depth < hiwater - (HHH-DDD) + 2) trpt += DDD; disk2stack(); maxdepth -= DDD; hiwater -= DDD;if(verbose)printf("unzap %%d: %%d\n", CNT2, hiwater); if (trpt->o_pm&128) /* fairness alg */ { now._cnt[now._a_t&1] = trpt->bup.oval; _n = 1; trpt->o_pm &= ~128; depth--; trpt--; printf("%%3d: reversed fairness default move\n", depth); goto Q999; { int d; Trail *trl; now._last = 0; for (d = 1; d < depth; d++) { trl = getframe(depth-d); /* was (trpt-d) */ if (trl->pr != 0) { now._last = trl->pr - BASE; break; } } } now._last = (depth<1)?0:(trpt-1)->pr; now._event = trpt->o_event; if ((now._a_t&1) && depth <= A_depth) return; /* to checkcycles() */ t = trpt->o_t; _n = trpt->o_n; ot = trpt->o_ot; II = trpt->pr; tt = trpt->o_tt; this = pptr(II); To = trpt->o_To; _m = trpt->o_m; ooi = trpt->oo_i; _m = do_reverse(t, II, _m);R999: /* jumps here when done */ printf("%%3d: proc %%d ", depth, II); printf("reverses %%d, %%d to %%d,", t->forw, tt, t->st); printf(" %%s [abit=%%d,adepth=%%d,", t->tp, now._a_t, A_depth); printf("tau=%%d,%%d]\n", trpt->tau, (trpt-1)->tau); /* pass the proviso tags */ if ((trpt->tau&8) /* rv or atomic */ && (trpt->tau&16)) && (trpt->tau&64)) depth--; trpt--; (trans[ot][tt])->om = _m; /* head of list */ /* i.e., not set if rv fails */ if (_m)#if defined(VERI) && !defined(NP) if (II == 0 && verbose && !reached[ot][t->st]) { printf("depth %%d: Claim reached state %%d (line %%d)\n", depth, t->st, src_claim [t->st]); fflush(stdout); else trpt->e_state = 0; /* undo */ if (_m>_n||(_n>3&&_m!=0)) _n=_m; ((P0 *)this)->_p = tt; } /* all options */ if (!t && ooi > 0) printf("randomizer: continue for %%d more\n", ooi); goto DOMORE; else printf("randomizer: done\n"); /* Fairness: undo Rule 2 */ if ((trpt->o_pm&32) && (trpt->o_pm&64)) { if (trpt->o_pm&1) if (now._cnt[now._a_t&1] == 1) now._cnt[now._a_t&1] = 2; now._cnt[now._a_t&1] += 1; printf("undo Rule 2, cnt=%%d, _a_t=%%d\n", trpt->o_pm &= ~(32|64); { if (_n > 0) trpt->o_pm &= ~64; II = From+1; } } } if (II == 0) break; /* never claim */ } /* all processes */ /* Fairness: undo Rule 2 */ if (trpt->o_pm&32) /* remains if proc blocked */ if (now._cnt[now._a_t&1] == 1) now._cnt[now._a_t&1] = 2; now._cnt[now._a_t&1] += 1; printf("%%3d: proc -- fairness ", depth); trpt->o_pm &= ~32; && _n == 0 /* nobody moved */ && !(trpt->tau&4) /* in program move */ && !(trpt->tau&8) /* not an atomic one */#ifdef OTIM && ((trpt->tau&1) || endstate())#ifdef ETIM && (trpt->tau&1) /* already tried timeout */ /* see below */ && !((trpt->tau&32) && (_n == 0 || (trpt->tau&16))) && now._cnt[now._a_t&1] > 0) /* needed more procs */ { depth++; trpt++; trpt->o_pm |= 128 | ((trpt-1)->o_pm&(2|4)); trpt->bup.oval = now._cnt[now._a_t&1]; now._cnt[now._a_t&1] = 1; trpt->tau = 4; trpt->tau = 0; From = now._nr_pr-1; To = BASE; printf("%%3d: fairness default move ", depth); printf("(all procs block)\n"); goto Down;Q999: /* returns here with _n>0 when done */; if (trpt->o_pm&8) { now._a_t &= ~2; now._cnt[now._a_t&1] = 0; trpt->o_pm &= ~8; printf("%%3d: fairness undo Rule 1, _a_t=%%d\n", depth, now._a_t); if (trpt->o_pm&16) { now._a_t |= 2; trpt->o_pm &= ~16; printf("%%3d: fairness undo Rule 3, _a_t=%%d\n", /* preselected move - no successors outside stack */ if ((trpt->tau&32) && !(trpt->tau&64)) { From = now._nr_pr-1; To = BASE; printf("%%3d: proc %%d UnSelected (_n=%%d, tau=%%d)\n", depth, II+1, _n, trpt->tau); _n = 0; trpt->tau &= ~(16|32|64); if (II >= BASE) /* II already decremented */ goto Resume; else /* at least one move that was preselected at this */ /* level, blocked or truncated at the next level */ if ((trpt->tau&32) && (_n == 0 || (trpt->tau&16))) depth, II+1, (int) _n, trpt->tau); if (a_cycles && (trpt->tau&16)) { if (!(now._a_t&1)) printf("%%3d: setting proviso bit\n", depth); (trpt-1)->proviso = 1; trpt->proviso = 1; if ((trpt-1)->ostate) ((char *)&((trpt-1)->ostate->state))[0] |= 128; ((char *)&(trpt->ostate->state))[0] |= 128; (trpt-1)->ostate->proviso = 1; trpt->ostate->proviso = 1; From = now._nr_pr-1; To = BASE; _n = 0; trpt->tau &= ~(16|32|64); goto Again; /* do full search */ } /* else accept reduction */ _n = 0; trpt->tau &= ~(16|32|64); if (II >= BASE) /* already decremented */ goto Resume; goto Again; if (_n == 0 || ((trpt->tau&4) && (trpt->tau&2))) printf("%%3d: no move [II=%%d, tau=%%d, boq=%%d]\n", depth, II, trpt->tau, boq); /* ok if a rendez-vous fails: */ if (boq != -1) goto Done; /* ok if no procs or we're at maxdepth */ if ((now._nr_pr == 0 && (!strict || qs_empty())) || endstate() || depth >= maxdepth-1) goto Done; if ((trpt->tau&8) && !(trpt->tau&4)) { trpt->tau &= ~(1|8); /* 1=timeout, 8=atomic */ From = now._nr_pr-1; To = BASE; printf("%%3d: atomic step proc %%d ", depth, II+1); printf("unexecutable\n"); trpt->tau |= 4; /* switch to claim */ goto AllOver; if (!(trpt->tau&1)) /* didn't try timeout yet */ if (trpt->tau&4)#ifndef NTIM if (trpt->tau&2) /* requested */ { trpt->tau |= 1; trpt->tau &= ~2; goto Stutter; { /* only claim can enable timeout */ if ((trpt->tau&8) && !((trpt-1)->tau&4))/* blocks inside an atomic */ goto BreakOut; printf("%%d: req timeout\n", depth); (trpt-1)->tau |= 2; /* request */ printf("%%d: timeout\n", depth); trpt->tau |= 1;BreakOut:#ifndef NOSTUTTER if (!(trpt->tau&4)) { trpt->tau |= 4; /* claim stuttering */ trpt->tau |= 128; /* stutter mark */ printf("%%d: claim stutter\n", depth); goto Stutter; ; if (!noends && !a_cycles && !endstate()) { depth--; trpt--; /* new 4.2.3 */ uerror("invalid end state"); else if (a_cycles && (trpt->o_pm&2)) /* new 4.2.4 */ { depth--; trpt--; uerror("accept stutter");Done: if (!(trpt->tau&8)) /* not in atomic seqs */ if (_n != 0 /* --after-- a program-step, i.e., */ /* after backtracking a claim-step */ && (trpt->tau&4) /* with at least one running process */ /* unless in a stuttered accept state */ && ((now._nr_pr > 1) || (trpt->o_pm&2)) && !(now._a_t&1)) if (fairness) printf("Consider check %%d %%d...\n", now._a_t, now._cnt[0]); if ((now._a_t&2) /* A-bit */ && (now._cnt[0] == 1)) checkcycles(); checkcycles();#ifndef MA if (boq == -1 && (((trpt->tau&4) && !(trpt->tau&128)) || ( (trpt-1)->tau&128))) if (boq == -1) printf("%%d: zapping %%u (%%d)\n", depth, trpt->ostate, (trpt->ostate)?trpt->ostate->tagged:0); onstack_zap(); printf("%%d: zapping\n", depth); if (trpt->proviso) gstore((char *) &now, vsize, 1); if (depth > 0) goto Up;} void new_state(void) { /* place holder */ }assert(int a, char *s, int ii, int tt, Trans *t) if (!a && !noasserts) { char bad[1024]; strcpy(bad, "assertion violated "); if (strlen(s) > 1000) { strncpy(&bad[19], (const char *) s, 1000); bad[1019] = '\0'; strcpy(&bad[19], s); uerror(bad);#ifndef NOBOUNDCHECKBoundcheck(int x, int y, int a1, int a2, Trans *a3) assert((x >= 0 && x < y), "- invalid array index", a1, a2, a3); return x;wrap_stats(void) if (nShadow>0) printf("%%8g states, stored (%%g visited)\n", nstates - nShadow, nstates); printf("%%8g states, stored\n", nstates); printf(" %%8g nominal states (- rv and atomic)\n", nstates-midrv-nlinks+revrv); printf(" %%8g rvs succeeded\n", midrv-failedrv); printf(" %%8g nominal states (stored-atomic)\n", nstates-nlinks); printf(" %%8g midrv\n", midrv); printf(" %%8g failedrv\n", failedrv); printf(" %%8g revrv\n", revrv); printf("%%8g states, matched\n", truncs); printf("%%8g matches within stack\n",truncs2); printf("%%8g transitions (= visited+matched)\n", nstates+truncs); printf("%%8g transitions (= stored+matched)\n", printf("%%8g atomic steps\n", nlinks); if (nlost) printf("%%g lost messages\n", (double) nlost); printf("hash conflicts: %%g (resolved)\n", hcmp); printf("%%8g states allocated for dfs stack\n", ngrabs); printf("\nhash factor: %%4g (best if > 100.)\n\n", (double)(1<<(ssize-8)) / (double) nstates * 256.0); printf("bits set per state: %%u (-k%%u)\n", hfns, hfns);#if 0 printf("total bits available: %%8g (-M%%ld)\n", ((double) udmem) * 8.0, udmem/(1024L*1024L)); printf("total bits available: %%8g (-w%%d)\n", ((double) (1L << (ssize-4)) * 16.0), ssize);#ifdef COVEST /* this code requires compilation with -lm on some systems */ { double pow(double, double); double log(double); unsigned int best_k; double i, n = 30000.0L; double f, p, q, m, c, est = 0.0L, k = (double)hfns; c = (double) nstates / n; m = (double) (1<<(ssize-8)) * 256.0L / c; p = 1.0L - (k / m); q = 1.0L; for (i = 0.0L; i - est < n; i += 1.0L) { q *= p; est += pow(1.0L - q, k); f = m/i; est *= c; i *= c; /* account for loss from enhanced double hashing */ if (hfns > 2) est += i * pow(0.5, (double) ssize * 2.0); if (f < 1.134) best_k = 1; else if (f < 2.348) best_k = 2; else if (f < 3.644) best_k = 3; else best_k = (unsigned int) (pow(3.8L,1.0L/(f+4.2L))*f*.69315L + 0.99999999L); if (best_k != hfns && best_k > ssize) best_k = (unsigned int) 1.0 + ssize/log((double)best_k / (double)ssize + 3.0); if (best_k > 32) best_k = 1 + (unsigned int) (32.0/log((double)best_k/35.0)); if (est * (double) nstates < 1.0) { printf("prob. of omissions: negligible\n"); return; /* no hints needed */ if (best_k != hfns) { printf("hint: repeating the search with -k%%u ", best_k); printf("may increase accuracy\n"); { printf("hint: the current setting for -k (-k%%d) ", hfns); printf("is likely to be optimal for -w%%d\n", ssize); if (ssize < 32) { printf("hint: increasing -w above -w%%d ", ssize); printf("will increase accuracy (max is -w34)\n"); printf("(in xspin, increase Estimated State Space Size)\n");wrapup(void)#if defined(BITSTATE) || !defined(NOCOMP) double nr1, nr2, nr3 = 0.0, nr4, nr5 = 0.0;#if !defined(MA) && (defined(MEMCNT) || defined(MEMLIM)) int mverbose = 1; int mverbose = verbose; signal(SIGINT, SIG_DFL); printf("(%%s)\n", Version); if (!done) printf("Warning: Search not completed\n"); (void) unlink((const char *)stackfile); printf(" + Using Breadth-First Search\n"); printf(" + Partial Order Reduction\n");#ifdef COLLAPSE printf(" + Compression\n"); printf(" + Graph Encoding (-DMA=%%d)\n", MA);#ifdef R_XPT printf(" Restarted from checkpoint %%s.xpt\n", Source); printf(" + FullStack Matching\n"); printf(" + CntrStack Matching\n"); printf("\nBit statespace search for:\n");#ifdef HC printf("\nHash-Compact %%d search for:\n", HC); printf("\nFull statespace search for:\n"); printf(" notrace assertion +\n"); printf(" trace assertion +\n"); printf(" never claim +\n"); printf(" assertion violations "); if (noasserts) printf("- (disabled by -A flag)\n"); printf("+ (if within scope of claim)\n");#ifdef NOCLAIM printf(" never claim - (not selected)\n"); printf(" never claim - (none specified)\n"); printf("+\n"); printf(" non-progress cycles "); printf(" acceptance cycles "); if (a_cycles) printf("+ (fairness %%sabled)\n", fairness?"en":"dis"); else printf("- (not selected)\n"); printf(" cycle checks - (disabled by -DSAFETY)\n"); printf(" invalid end states - "); printf("(disabled by "); if (noends) printf("-E flag)\n\n"); printf("never claim)\n\n"); printf(" invalid end states "); printf("- (disabled by -E flag)\n\n"); printf("+\n\n"); printf("State-vector %%d byte, depth reached %%d", hmax, mreached); printf(", errors: %%d\n", errors); if (done) { extern void dfa_stats(void); if (maxgs+a_cycles+2 < MA) printf("MA stats: -DMA=%%d is sufficient\n", maxgs+a_cycles+2); dfa_stats(); wrap_stats(); printf("stackframes: %%d/%%d\n\n", smax, svmax); printf("stats: fa %%d, fh %%d, zh %%d, zn %%d - ", Fa, Fh, Zh, Zn); printf("check %%d holds %%d\n", Ccheck, Cholds); printf("stack stats: puts %%d, probes %%d, zaps %%d\n", PUT, PROBE, ZAPS); printf("\n"); nr1 = (nstates-nShadow)* (double)(hmax+sizeof(struct H_el)-sizeof(unsigned)); nr2 = 0.0; nr2 = (double) ((maxdepth+3)*sizeof(Trail));#if !defined(MA) || defined(COLLAPSE) nr3 = (double) (1L< 0.0) printf("%%-6.3f memory used for bit stack\n", nr5/1000000.); remainder = remainder - nr3 - nr5; printf("%%-6.3f actual memory usage for states", tmp_nr/1000000.); remainder = remainder - tmp_nr; printf(" ("); if (tmp_nr > 0.) { if (tmp_nr > nr1) printf("unsuccessful "); printf("compression: %%.2f%%%%)\n", (100.0*tmp_nr)/nr1); printf("less than 1k)\n"); { printf(" State-vector as stored = %%.0f byte", (tmp_nr)/(nstates-nShadow) - (double) (sizeof(struct H_el) - sizeof(unsigned))); printf(" + %%ld byte overhead\n", sizeof(struct H_el)-sizeof(unsigned)); printf("%%-6.3f memory used for hash table (-w%%d)\n", remainder = remainder - nr3; printf("%%-6.3f memory used for DFS stack (-m%%ld)\n", nr2/1000000., maxdepth); remainder = remainder - nr2; if (remainder - fragment > 0.0) printf("%%-6.3f other (proc and chan stacks)\n", (remainder-fragment)/1000000.); if (fragment > 0.0) printf("%%-6.3f memory lost to fragmentation\n", fragment/1000000.); printf("%%-6.3f total actual memory usage\n\n", memcnt/1000000.); printf("%%-6.3f memory usage (Mbyte)\n\n", printf("nr of templates: [ globals chans procs ]\n"); printf("collapse counts: [ "); { int i; for (i = 0; i < 256+2; i++) if (ncomps[i] != 0) printf("%%d ", ncomps[i]); printf("]\n"); if ((done || verbose) && !no_rck) do_reach(); { int i; printf("\nPeg Counts (transitions executed):\n"); for (i = 1; i < NTRANS; i++) { if (peg[i]) putpeg(i, peg[i]); } }#ifdef VAR_RANGES dumpranges(); if (vprefix > 0) close(svfd);stopped(int arg){ printf("Interrupted\n"); wrapup(); * based on Bob Jenkins hash-function from 1996 * see: http://www.burtleburtle.net/bob/#if defined(HASH64) || defined(WIN64)#define mix(a,b,c) \{ a -= b; a -= c; a ^= (c>>43); \ b -= c; b -= a; b ^= (a<<9); \ c -= a; c -= b; c ^= (b>>8); \ a -= b; a -= c; a ^= (c>>38); \ b -= c; b -= a; b ^= (a<<23); \ c -= a; c -= b; c ^= (b>>5); \ a -= b; a -= c; a ^= (c>>35); \ b -= c; b -= a; b ^= (a<<49); \ c -= a; c -= b; c ^= (b>>11); \ a -= b; a -= c; a ^= (c>>12); \ b -= c; b -= a; b ^= (a<<18); \ c -= a; c -= b; c ^= (b>>22); \{ a -= b; a -= c; a ^= (c>>13); \ b -= c; b -= a; b ^= (a<<8); \ c -= a; c -= b; c ^= (b>>13); \ b -= c; b -= a; b ^= (a<<16); \ a -= b; a -= c; a ^= (c>>3); \ b -= c; b -= a; b ^= (a<<10); \ c -= a; c -= b; c ^= (b>>15); \d_hash(uchar *Cp, int Om) /* double bit hash - Jenkins */{ unsigned long a = 0x9e3779b9, b, c = 0, len, length; unsigned long *k = (unsigned long *) Cp; length = len = (unsigned long) ((unsigned long) Om + WS-1)/WS; b = HASH_CONST[HASH_NR]; while (len >= 3) { a += k[0]; b += k[1]; c += k[2]; mix(a,b,c); k += 3; len -= 3; c += length; switch (len) { case 2: b += k[1]; case 1: a += k[0]; mix(a,b,c); j1 = c&nmask; j3 = a&7; j2 = b&nmask; j4 = (a>>3)&7; K1 = c; K2 = b;s_hash(uchar *cp, int om){ d_hash(cp, om); /* sets K1 and K2 */ if (S_Tab == H_tab) j1 = K1 %% omaxdepth; if (ssize < 8*WS) j1 = K1&mask; j1 = K1;#ifndef RANDSTORint *prerand;inirand(void) srand(123); /* fixed startpoint */ prerand = (int *) emalloc((omaxdepth+3)*sizeof(int)); for (i = 0; i < omaxdepth+3; i++) prerand[i] = rand();pan_rand(void){ if (!prerand) inirand(); return prerand[depth];main(int argc, char *argv[]){ void to_compile(void); efd = stderr; /* default */ bstore = bstore_reg; /* default */ while (argc > 1 && argv[1][0] == '-') { switch (argv[1][1]) { case 'a': fprintf(efd, "error: -a disabled"); usage(efd); break; case 'a': a_cycles = 1; break; case 'A': noasserts = 1; break; case 'b': bounded = 1; break; case 'c': upto = atoi(&argv[1][2]); break; case 'd': state_tables++; break; case 'e': every_error = 1; Nr_Trails = 1; break; case 'E': noends = 1; break; case 'F': if (strlen(argv[1]) > 2) stackfile = &argv[1][2]; break;#if !defined(SAFETY) && !defined(NOFAIR) case 'f': fairness = 1; break; case 'h': if (!argv[1][2]) usage(efd); else HASH_NR = atoi(&argv[1][2])%%33; break; case 'I': iterative = 2; every_error = 1; break; case 'i': iterative = 1; every_error = 1; break; case 'J': like_java = 1; break; /* Klaus Havelund */ case 'k': hfns = atoi(&argv[1][2]); break; case 'l': a_cycles = 1; break; case 'l': fprintf(efd, "error: -l disabled"); case 'M': udmem = atoi(&argv[1][2]); break; case 'G': udmem = atoi(&argv[1][2]); udmem *= 1024; break; case 'M': case 'G': fprintf(stderr, "-M and -G affect only -DBITSTATE\n"); case 'm': maxdepth = atoi(&argv[1][2]); break; case 'n': no_rck = 1; break; case 'p': vprefix = atoi(&argv[1][2]); break; case 'q': strict = 1; break; case 'r':samething: readtrail = 1; if (isdigit(argv[1][2])) whichtrail = atoi(&argv[1][2]); case 'P': readtrail = 1; onlyproc = atoi(&argv[1][2]); break; case 'C': coltrace = 1; goto samething; case 'g': gui = 1; goto samething; case 'S': silent = 1; break; case 'R': Nrun = atoi(&argv[1][2]); break; case 's': hfns = 1; break; case 'T': TMODE = 0444; break; case 't': if (argv[1][2]) tprefix = &argv[1][2]; break; case 'V': printf("Generated by %%s\n", Version); to_compile(); pan_exit(0); break; case 'v': verbose = 1; break; case 'w': ssize = atoi(&argv[1][2]); break; case 'Y': signoff = 1; break; case 'X': efd = stdout; break; default : fprintf(efd, "saw option -%%c\n", argv[1][1]); usage(efd); break; argc--; argv++; if (iterative && TMODE != 0666) { TMODE = 0666; fprintf(efd, "warning: -T ignored when -i or -I is used\n");#if defined(WIN32) || defined(WIN64) if (TMODE == 0666) TMODE = _S_IWRITE | _S_IREAD; TMODE = _S_IREAD;#ifdef OHASH fprintf(efd, "warning: -DOHASH no longer supported (directive ignored)\n");#ifdef JHASH fprintf(efd, "warning: -DJHASH no longer supported (directive ignored)\n");#ifdef HYBRID_HASH fprintf(efd, "warning: -DHYBRID_HASH no longer supported (directive ignored)\n");#ifdef NOCOVEST fprintf(efd, "warning: -DNOCOVEST no longer supported (directive ignored)\n");#ifdef BCOMP fprintf(efd, "warning: -DBCOMP no longer supported (directive ignored)\n"); if (hfns <= 0) { hfns = 1; fprintf(efd, "warning: using -k%%d as minimal usable value\n", hfns); omaxdepth = maxdepth; if (WS == 4 && ssize > 34) { ssize = 34; fprintf(efd, "warning: using -w%%d as max usable value\n", ssize); * -w35 would not work: 35-3 = 32 but 1^31 is the largest * power of 2 that can be represented in an unsigned long if (WS == 4 && ssize > 27) { ssize = 27; * for emalloc, the lookup table size multiplies by 4 for the pointers * the largest power of 2 that can be represented in a ulong is 1^31 * hence the largest number of lookup table slots is 31-4 = 27 hiwater = HHH = maxdepth-10; DDD = HHH/2; if (!stackfile) { stackfile = (char *) emalloc(strlen(Source)+4+1); sprintf(stackfile, "%%s._s_", Source); if (iterative) { fprintf(efd, "error: cannot use -i or -I with -DSC\n");#if (defined(R_XPT) || defined(W_XPT)) && !defined(MA) fprintf(efd, "error: -D?_XPT requires -DMA\n"); exit(1); if (iterative && a_cycles) fprintf(efd, "warning: -i or -I work for safety properties only\n");#if defined(SC) fprintf(efd, "error: -DBFS not compatible with -DSC\n");#if defined(HAS_LAST) fprintf(efd, "error: -DBFS not compatible with _last\n");#if defined(REACH) fprintf(efd, "warning: -DREACH redundant when -DBFS is used\n");#if defined(HAS_STACK) fprintf(efd, "error: cannot use UnMatched qualifier on c_track with BFS\n");#if defined(MERGED) && defined(PEG) fprintf(efd, "error: to allow -DPEG use: spin -o3 -a %%s\n", Source); fprintf(efd, " to turn off transition merge optimization\n"); pan_exit(1);#ifdef NOCOMP fprintf(efd, "error: cannot combine -DHC and -DNOCOMP\n"); fprintf(efd, "error: cannot combine -DHC and -DBITSTATE\n");#if defined(SAFETY) && defined(NP) fprintf(efd, "error: cannot combine -DNP and -DSAFETY\n"); fprintf(efd, "error: cannot combine -DMA and -DBITSTATE\n"); if (MA <= 0) { fprintf(efd, "usage: -DMA=N with N > 0 and < VECTORSZ\n");#if defined(BITSTATE) fprintf(efd, "error: cannot combine -DBITSTATE and -DCOLLAPSE\n");#if defined(NOCOMP) fprintf(efd, "error: cannot combine -DNOCOMP and -DCOLLAPSE\n"); if (maxdepth <= 0 || ssize <= 1) usage(efd);#if SYNC>0 && !defined(NOREDUCE) if (a_cycles && fairness) { fprintf(efd, "error: p.o. reduction not compatible with "); fprintf(efd, "fairness (-f) in models\n"); fprintf(efd, " with rendezvous operations: "); fprintf(efd, "recompile with -DNOREDUCE\n"); pan_exit(1);#if defined(REM_VARS) && !defined(NOREDUCE) { fprintf(efd, "warning: p.o. reduction not compatible with "); fprintf(efd, "remote varrefs (use -DNOREDUCE)\n");#if defined(NOCOMP) && !defined(BITSTATE) { fprintf(efd, "error: -DNOCOMP voids -l and -a\n");#ifdef MEMLIM memlim = (double) MEMLIM * (double) (1<<20); /* size in Mbyte */#ifdef MEMCNT#if MEMCNT<31 memlim = (double) (1< 1) HASH_NR = Nrun - 1; if (Nrun < 1 || Nrun > 32) { fprintf(efd, "error: invalid arg for -R\n"); usage(efd); if (fairness && !a_cycles) { fprintf(efd, "error: -f requires -a or -l\n");#if ACCEPT_LAB==0 { fprintf(efd, "error: no accept labels defined "); fprintf(efd, "in model (for option -a)\n"); { fprintf(efd, "warning: no explicit accept labels "); fprintf(efd, "defined in model (for -a)\n");#if !defined(NOREDUCE)#if defined(HAS_ENABLED) fprintf(efd, "error: reduced search precludes "); fprintf(efd, "use of 'enabled()'\n");#if defined(HAS_PCVALUE) fprintf(efd, "use of 'pcvalue()'\n");#if defined(HAS_BADELSE) fprintf(efd, "using 'else' combined with i/o stmnts\n"); fprintf(efd, "use of _last\n"); fprintf(efd, "warning: use of a rendezvous stmnts in the escape\n"); fprintf(efd, " of an unless clause, if present, could make p.o. reduction\n"); fprintf(efd, " invalid (use -DNOREDUCE to avoid this)\n"); fprintf(efd, " (this type of rv is also not compatible with -DBFS)\n");#if SYNC>0 && defined(BFS) fprintf(efd, "warning: use of rendezvous in BFS mode "); fprintf(efd, "does not preserve all invalid endstates\n");#if !defined(REACH) && !defined(BITSTATE) if (iterative != 0 && a_cycles == 0) fprintf(efd, "warning: -i and -I need -DREACH to work accurately\n");#if defined(BITSTATE) && defined(REACH) fprintf(efd, "warning: -DREACH voided by -DBITSTATE\n");#if defined(MA) && defined(REACH) fprintf(efd, "warning: -DREACH voided by -DMA\n");#if defined(FULLSTACK) && defined(CNTRSTACK) fprintf(efd, "error: cannot combine"); fprintf(efd, " -DFULLSTACK and -DCNTRSTACK\n");#if defined(VERI) if (!a_cycles && !state_tables) { fprintf(efd, "warning: never claim + accept labels "); fprintf(efd, "requires -a flag to fully verify\n"); if ( !readtrail { fprintf(efd, "warning: verification in BFS mode "); fprintf(efd, "is restricted to safety properties\n"); && !state_tables) { fprintf(efd, "hint: this search is more efficient "); fprintf(efd, "if pan.c is compiled -DSAFETY\n"); S_A = 0; { if (!fairness) S_A = 1; /* _a_t */ else /* _a_t and _cnt[NFAIR] */ S_A = (&(now._cnt[0]) - (uchar *) &now) + NFAIR - 2; /* -2 because first two uchars in now are masked */ signal(SIGINT, stopped); if (WS == 4 && ssize >= 32) { mask = 0xffffffff; switch (ssize) { case 34: nmask = (mask>>1); break; case 33: nmask = (mask>>2); break; default: nmask = (mask>>3); break; nmask = mask; } else if (WS == 8) { mask = ((1L<>3; } else if (WS != 4) { fprintf(stderr, "pan: wordsize %%ld not supported\n", WS); exit(1); } else /* WS == 4 and ssize < 32 */ nmask = (mask>>3); trail = (Trail *) emalloc(6*sizeof(Trail)); trail += 3; trail = (Trail *) emalloc((maxdepth+3)*sizeof(Trail)); trail++; /* protect trpt-1 refs at depth 0 */ { char nm[64]; sprintf(nm, "%%s.svd", Source); if ((svfd = creat(nm, 0666)) < 0) { fprintf(efd, "couldn't create %%s\n", nm); vprefix = 0;#if SYNC>0 && ASYNC==0 set_recvs(); run(); done = 1;usage(FILE *fd) fprintf(fd, "Valid Options are:\n"); fprintf(fd, " -a -> is disabled by -DNP "); fprintf(fd, "(-DNP compiles for -l only)\n"); fprintf(fd, " -a find acceptance cycles\n"); fprintf(fd, " -a,-l,-f -> are disabled by -DSAFETY\n"); fprintf(fd, " -A ignore assert() violations\n"); fprintf(fd, " -b consider it an error to exceed the depth-limit\n"); fprintf(fd, " -cN stop at Nth error "); fprintf(fd, "(defaults to -c1)\n"); fprintf(fd, " -d print state tables and stop\n"); fprintf(fd, " -e create trails for all errors\n"); fprintf(fd, " -E ignore invalid end states\n"); fprintf(fd, " -Ffile use 'file' to store disk-stack\n"); fprintf(fd, " -f add weak fairness (to -a or -l)\n"); fprintf(fd, " -hN use different hash-seed N:1..32\n"); fprintf(fd, " -i search for shortest path to error\n"); fprintf(fd, " -I like -i, but approximate and faster\n"); fprintf(fd, " -J reverse eval order of nested unlesses\n"); fprintf(fd, " -kN set N bits per state (defaults to 3)\n"); fprintf(fd, " -l find non-progress cycles\n"); fprintf(fd, " -l find non-progress cycles -> "); fprintf(fd, "disabled, requires "); fprintf(fd, "compilation with -DNP\n"); fprintf(fd, " -MN use N Megabytes for bitstate hash array\n"); fprintf(fd, " -GN use N Gigabytes for bitstate hash array\n"); fprintf(fd, " -mN max depth N steps (default=10k)\n"); fprintf(fd, " -n no listing of unreached states\n"); fprintf(fd, " -pN create svfile (save N bytes per state)\n"); fprintf(fd, " -q require empty chans in valid end states\n"); fprintf(fd, " -r read and execute trail - can add -v,-n,-PN,-g,-C\n"); fprintf(fd, " -rN read and execute N-th error trail\n"); fprintf(fd, " -C read and execute trail - columnated output (can add -v,-n)\n"); fprintf(fd, " -PN read and execute trail - restrict trail output to proc N\n"); fprintf(fd, " -g read and execute trail + msc gui support\n"); fprintf(fd, " -S silent replay: only user defined printfs show\n"); fprintf(fd, " -RN repeat run Nx with N "); fprintf(fd, "[1..32] independent hash functions\n"); fprintf(fd, " -s same as -k1 (single bit per state)\n"); fprintf(fd, " -T create trail files in read-only mode\n"); fprintf(fd, " -tsuf replace .trail with .suf on trailfiles\n"); fprintf(fd, " -V print SPIN version number\n"); fprintf(fd, " -v verbose -- filenames in unreached state listing\n"); fprintf(fd, " -wN hashtable of 2^N entries "); fprintf(fd, "(defaults to -w%%d)\n", ssize);Malloc(unsigned long n){ char *tmp;#if defined(MEMCNT) || defined(MEMLIM) if (memcnt+ (double) n > memlim) goto err;#if 1 tmp = (char *) malloc(n); if (!tmp) tmp = (char *) sbrk(n); if (tmp == (char *) -1L)err: printf("pan: out of memory\n"); printf(" %%g bytes used\n", memcnt); printf(" %%g bytes more needed\n", (double) n); printf(" %%g bytes limit\n", memlim); printf("hint: to reduce memory, recompile with\n"); printf(" -DMA=%%d # better/slower compression, or\n", hmax); printf(" -DBITSTATE # supertrace, approximation\n");#ifndef HC printf(" -DCOLLAPSE # good, fast compression, or\n"); printf(" -DHC # hash-compaction, approximation\n"); memcnt += (double) n; return tmp;#define CHUNK (100*VECTORSZ)emalloc(unsigned long n) /* never released or reallocated */ if (n == 0) return (char *) NULL; if (n&(sizeof(void *)-1)) /* for proper alignment */ n += sizeof(void *)-(n&(sizeof(void *)-1)); if ((unsigned long) left < n) { grow = (n < CHUNK) ? CHUNK : n; have = Malloc(grow); fragment += (double) left; left = grow; tmp = have; have += (long) n; left -= (long) n; memset(tmp, 0, n);Uerror(char *str){ /* always fatal */ uerror(str);#if defined(MA) && !defined(SAFETY)Unwind(void){ Trans *t; uchar ot, _m; int tt; short II; int i; uchar oat = now._a_t; now._a_t &= ~(1|16|32); memcpy((char *) &comp_now, (char *) &now, vsize); now._a_t = oat; trpt = getframe(depth); printf("%%d State: ", depth); for (i = 0; i < vsize; i++) printf("%%d%%s,", ((char *)&now)[i], Mask[i]?"*":""); if (trpt->o_pm&128) /* fairness alg */ { now._cnt[now._a_t&1] = trpt->bup.oval; depth--; trpt = getframe(depth); trpt--; goto Q999; { int d; Trail *trl; now._last = 0; for (d = 1; d < depth; d++) { trl = getframe(depth-d); /* was trl = (trpt-d); */ if (trl->pr != 0) { now._last = trl->pr - BASE; break; } } } now._last = (depth<1)?0:(trpt-1)->pr; now._event = trpt->o_event; if ((now._a_t&1) && depth <= A_depth) { now._a_t &= ~(1|16|32); if (fairness) now._a_t |= 2; /* ? */ A_depth = 0; goto CameFromHere; /* checkcycles() */ t = trpt->o_t; ot = trpt->o_ot; II = trpt->pr; tt = trpt->o_tt; this = pptr(II); _m = do_reverse(t, II, trpt->o_m); printf("%%3d: proc %%d ", depth, II); printf("reverses %%d, %%d to %%d,", t->forw, tt, t->st); printf(" %%s [abit=%%d,adepth=%%d,", t->tp, now._a_t, A_depth); printf("tau=%%d,%%d] \n", trpt->tau, (trpt-1)->tau); depth--; trpt--; /* reached[ot][t->st] = 1; 3.4.13 */ ((P0 *)this)->_p = tt; if ((trpt->o_pm&32)) if (now._cnt[now._a_t&1] == 0) now._cnt[now._a_t&1] = 1;Q999: now._a_t |= 2;CameFromHere: if (memcmp((char *) &now, (char *) &comp_now, vsize) == 0) return depth;static char unwinding;uerror(char *str){ static char laststr[256]; int is_cycle; if (unwinding) return; /* 1.4.2 */ if (strncmp(str, laststr, 254)) printf("pan: %%s (at depth %%ld)\n", str, (depthfound==-1)?depth:depthfound); strncpy(laststr, str, 254); errors++; if (readtrail) { wrap_trail(); return; } is_cycle = (strstr(str, " cycle") != (char *) 0); if (!is_cycle) if ((every_error != 0) || errors == upto) if (is_cycle) { int od = depth; unwinding = 1; depthfound = Unwind(); unwinding = 0; depth = od; if (depth > 1) trpt--; nuerror(str); if (depth > 1) trpt++; putrail(); if (strstr(str, " cycle")) { if (every_error) printf("sorry: MA writes 1 trail max\n"); wrapup(); /* no recovery from unwind */ { depth--; trpt--; /* undo */ if (iterative != 0 && maxdepth > 0) { maxdepth = (iterative == 1)?(depth-1):(depth/2); warned = 1; printf("pan: reducing search depth to %%ld\n", maxdepth); depthfound = -1;xrefsrc(int lno, S_F_MAP *mp, int M, int i){ Trans *T; int j, retval=1; for (T = trans[M][i]; T; T = T->nxt) if (T && T->tp) { if (strcmp(T->tp, ".(goto)") == 0 || strncmp(T->tp, "goto :", 6) == 0) return 1; /* not reported */ printf("\tline %%d", lno); for (j = 0; j < sizeof(mp); j++) if (i >= mp[j].from && i <= mp[j].upto) { printf(", \"%%s\"", mp[j].fnm); printf(", state %%d", i); if (strcmp(T->tp, "") != 0) { char *q; q = transmognify(T->tp); printf(", \"%%s\"", q?q:""); } else if (stopstate[M][i]) printf(", -end state-"); retval = 0; /* reported */ return retval;r_ck(uchar *which, int N, int M, short *src, S_F_MAP *mp){ int i, m=0; if (M == VERI && !verbose) return; printf("unreached in proctype %%s\n", procname[M]); for (i = 1; i < N; i++) if (which[i] == 0 && (mapstate[M][i] == 0 || which[mapstate[M][i]] == 0)) m += xrefsrc((int) src[i], mp, M, i); else m++; printf(" (%%d of %%d states)\n", N-1-m, N-1);putrail(void){ int fd; long i, j; Trail *trl;#if defined VERI || defined(MERGED) char snap[64]; fd = make_trail(); for (i = 1; i <= depth; i++) { if (i == depthfound+1) write(fd, "-1:-1:-1\n", 9); trl = getframe(i); if (!trl->o_t) continue; if (trl->o_pm&128) continue; sprintf(snap, "%%ld:%%d:%%d\n", i, trl->pr, trl->o_t->t_id); { printf("pan: error writing trailfile\n"); close(fd); wrapup();sv_save(void) /* push state vector onto save stack */{ if (!svtack->nxt) { svtack->nxt = (Svtack *) emalloc(sizeof(Svtack)); svtack->nxt->body = emalloc(vsize*sizeof(char)); svtack->nxt->lst = svtack; svtack->nxt->m_delta = vsize; svmax++; } else if (vsize > svtack->nxt->m_delta) { svtack->nxt->body = emalloc(vsize*sizeof(char)); svtack = svtack->nxt; svtack->o_boq = boq; svtack->o_delta = vsize; /* don't compress */ memcpy((char *)(svtack->body), (char *) &now, vsize); printf("%%d: sv_save\n", depth);sv_restor(void) /* pop state vector from save stack */ memcpy((char *)&now, svtack->body, svtack->o_delta); boq = svtack->o_boq;#ifdef HAS_STACK c_unstack((uchar *) &(svtack->c_stack[0])); c_revert((uchar *) &(now.c_state[0])); if (vsize != svtack->o_delta) Uerror("sv_restor"); if (!svtack->lst) Uerror("error: v_restor"); svtack = svtack->lst; printf(" sv_restor\n");p_restor(int h){ int i; char *z = (char *) &now; proc_offset[h] = stack->o_offset; proc_skip[h] = (uchar) stack->o_skip;#ifndef XUSAFE p_name[h] = stack->o_name; for (i = vsize + stack->o_skip; i > vsize; i--) Mask[i-1] = 1; /* align */ vsize += stack->o_skip; memcpy(z+vsize, stack->body, stack->o_delta); vsize += stack->o_delta;#ifndef NOVSZ now._vsz = vsize; for (i = 1; i <= Air[((P0 *)pptr(h))->_t]; i++) Mask[vsize - i] = 1; /* pad */ Mask[proc_offset[h]] = 1; /* _pid */ if (BASE > 0 && h > 0) ((P0 *)pptr(h))->_pid = h-BASE; ((P0 *)pptr(h))->_pid = h; i = stack->o_delqs; now._nr_pr += 1; if (!stack->lst) /* debugging */ Uerror("error: p_restor"); stack = stack->lst; this = pptr(h); while (i-- > 0) q_restor();q_restor(void){ char *z = (char *) &now; int k, k_end; q_offset[now._nr_qs] = stack->o_offset; q_skip[now._nr_qs] = (uchar) stack->o_skip; q_name[now._nr_qs] = stack->o_name; now._nr_qs += 1; k_end = stack->o_offset; k = k_end - stack->o_skip; if (q_zero(now._nr_qs)) k_end += stack->o_delta; for ( ; k < k_end; k++) Mask[k] = 1; Uerror("error: q_restor");typedef struct IntChunks { int *ptr; struct IntChunks *nxt;} IntChunks;IntChunks *filled_chunks[512];IntChunks *empty_chunks[512];int *grab_ints(int nr){ IntChunks *z; if (nr >= 512) Uerror("cannot happen grab_int"); if (filled_chunks[nr]) { z = filled_chunks[nr]; filled_chunks[nr] = filled_chunks[nr]->nxt; } else { z = (IntChunks *) emalloc(sizeof(IntChunks)); z->ptr = (int *) emalloc(nr * sizeof(int)); z->nxt = empty_chunks[nr]; empty_chunks[nr] = z; return z->ptr;ungrab_ints(int *p, int nr) if (!empty_chunks[nr]) Uerror("cannot happen ungrab_int"); z = empty_chunks[nr]; empty_chunks[nr] = empty_chunks[nr]->nxt; z->ptr = p; z->nxt = filled_chunks[nr]; filled_chunks[nr] = z;delproc(int sav, int h){ int d, i=0; int o_vsize = vsize; if (h+1 != (int) now._nr_pr) return 0; while (now._nr_qs && q_offset[now._nr_qs-1] > proc_offset[h]) { delq(sav); d = vsize - proc_offset[h]; if (sav) { if (!stack->nxt) { stack->nxt = (Stack *) emalloc(sizeof(Stack)); stack->nxt->body = emalloc(Maxbody*sizeof(char)); stack->nxt->lst = stack; smax++; stack = stack->nxt; stack->o_offset = proc_offset[h]; stack->o_skip = (int) proc_skip[h]; stack->o_skip = (short) proc_skip[h]; stack->o_name = p_name[h]; stack->o_delta = d; stack->o_delqs = i; memcpy(stack->body, (char *)pptr(h), d); vsize = proc_offset[h]; now._nr_pr = now._nr_pr - 1; memset((char *)pptr(h), 0, d); vsize -= (int) proc_skip[h]; for (i = vsize; i < o_vsize; i++) Mask[i] = 0; /* reset */delq(int sav){ int h = now._nr_qs - 1; int d = vsize - q_offset[now._nr_qs - 1]; int k, o_vsize = vsize; stack->o_offset = q_offset[h]; stack->o_skip = (int) q_skip[h]; stack->o_skip = (short) q_skip[h]; stack->o_name = q_name[h]; memcpy(stack->body, (char *)qptr(h), d); vsize = q_offset[h]; now._nr_qs = now._nr_qs - 1; memset((char *)qptr(h), 0, d); vsize -= (int) q_skip[h]; for (k = vsize; k < o_vsize; k++) Mask[k] = 0; /* reset */qs_empty(void) for (i = 0; i < (int) now._nr_qs; i++) { if (q_sz(i) > 0) return 0;endstate(void){ int i; P0 *ptr; for (i = BASE; i < (int) now._nr_pr; i++) { ptr = (P0 *) pptr(i); if (!stopstate[ptr->_t][ptr->_p]) if (strict) return qs_empty();#if defined(EVENT_TRACE) && !defined(OTIM) if (!stopstate[EVENT_TRACE][now._event] && !a_cycles) { printf("pan: event_trace not completed\n");checkcycles(void){ uchar o_a_t = now._a_t; uchar o_cnt = now._cnt[1]; struct H_el *sv = trpt->ostate; /* save */ uchar prov = trpt->proviso; /* save */ { int i; uchar *v = (uchar *) &now; printf(" set Seed state "); if (fairness) printf("(cnt = %%d:%%d, nrpr=%%d) ", now._cnt[0], now._cnt[1], now._nr_pr); /* for (i = 0; i < n; i++) printf("%%d,", v[i]); */ printf("\n"); printf("%%d: cycle check starts\n", depth); now._a_t |= (1|16|32); /* 1 = 2nd DFS; (16|32) to help hasher */ now._cnt[1] = now._cnt[0]; memcpy((char *)&A_Root, (char *)&now, vsize); A_depth = depthfound = depth; new_state(); /* start 2nd DFS */ now._a_t = o_a_t; now._cnt[1] = o_cnt; A_depth = 0; depthfound = -1; printf("%%d: cycle check returns\n", depth); trpt->ostate = sv; /* restore */ trpt->proviso = prov;#endif struct H_el *Free_list = (struct H_el *) 0;onstack_init(void) /* to store stack states in a bitstate search */{ S_Tab = (struct H_el **) emalloc(maxdepth*sizeof(struct H_el *));struct H_el *grab_state(int n){ struct H_el *v, *last = 0; if (H_tab == S_Tab) { for (v = Free_list; v && ((int) v->tagged >= n); v=v->nxt) { if ((int) v->tagged == n) { if (last) last->nxt = v->nxt;gotcha: Free_list = v->nxt; v->tagged = 0; v->nxt = 0; v->ln = 0; return v; Fh++; last=v; /* new: second try */ v = Free_list; if (v && ((int) v->tagged >= n)) goto gotcha; ngrabs++; return (struct H_el *) emalloc(sizeof(struct H_el)+n-sizeof(unsigned));#define grab_state(n) (struct H_el *) \ emalloc(sizeof(struct H_el)+n-sizeof(unsigned));unsigned longordinal(char *v, long n, short tp){ struct H_el *tmp, *ntmp; long m; struct H_el *olst = (struct H_el *) 0; s_hash((uchar *)v, n); tmp = H_tab[j1]; { tmp = grab_state(n); H_tab[j1] = tmp; for ( ;; olst = tmp, tmp = tmp->nxt) { m = memcmp(((char *)&(tmp->state)), v, n); if (n == tmp->ln) if (m == 0) goto done; if (m < 0)Insert: ntmp = grab_state(n); ntmp->nxt = tmp; if (!olst) H_tab[j1] = ntmp; olst->nxt = ntmp; tmp = ntmp; } else if (!tmp->nxt)Append: tmp->nxt = grab_state(n); tmp = tmp->nxt; if (n < tmp->ln) goto Insert; else if (!tmp->nxt) goto Append; m = ++ncomps[tp]; tmp->tagged = m; tmp->st_id = m; memcpy(((char *)&(tmp->state)), v, n); tmp->ln = n;done: return tmp->tagged; return tmp->st_id;compress(char *vin, int nin) /* collapse compression */{ char *w, *v = (char *) &comp_now; int i, j; unsigned long n; static char *x; static uchar nbytes[513]; /* 1 + 256 + 256 */ static unsigned short nbytelen; long col_q(int, char *); long col_p(int, char *); *v++ = now._a_t; if (fairness) for (i = 0; i < NFAIR; i++) *v++ = now._cnt[i]; nbytelen = 0;#ifndef JOINPROCS { n = col_p(i, (char *) 0);#ifdef NOFIX nbytes[nbytelen] = 0; nbytes[nbytelen] = 1; *v++ = ((P0 *) pptr(i))->_t; *v++ = n&255; if (n >= (1<<8)) { nbytes[nbytelen]++; *v++ = (n>>8)&255; if (n >= (1<<16)) *v++ = (n>>16)&255; if (n >= (1<<24)) *v++ = (n>>24)&255; nbytelen++; x = scratch; x += col_p(i, x); n = ordinal(scratch, x-scratch, 2); /* procs */ *v++ = n&255; nbytes[nbytelen] = 0; if (n >= (1<<8)) { nbytes[nbytelen]++; *v++ = (n>>8)&255; if (n >= (1<<16)) *v++ = (n>>16)&255; if (n >= (1<<24)) *v++ = (n>>24)&255; nbytelen++;#ifdef SEPQS { n = col_q(i, (char *) 0);#ifdef NOVSZ /* 3 = _a_t, _nr_pr, _nr_qs */ w = (char *) &now + 3 * sizeof(uchar); w += NFAIR;#if VECTORSZ<65536 w = (char *) &(now._vsz) + sizeof(unsigned short); w = (char *) &(now._vsz) + sizeof(unsigned long); *x++ = now._nr_pr; *x++ = now._nr_qs; if (now._nr_qs > 0 && qptr(0) < pptr(0)) n = qptr(0) - (uchar *) w; n = pptr(0) - (uchar *) w; j = w - (char *) &now; for (i = 0; i < (int) n; i++, w++) if (!Mask[j++]) *x++ = *w;#ifndef SEPQS x += col_q(i, x); x--; for (i = 0, j = 6; i < nbytelen; i++) { if (j == 6) { j = 0; *(++x) = 0; j += 2; *x |= (nbytes[i] << j); x++; for (j = 0; j < WS-1; j++) *x++ = 0; x -= j; j = 0; n = ordinal(scratch, x-scratch, 0); /* globals */ if (n >= (1<< 8)) { *v++ = (n>> 8)&255; j++; } if (n >= (1<<16)) { *v++ = (n>>16)&255; j++; } if (n >= (1<<24)) { *v++ = (n>>24)&255; j++; } *v++ = j; /* add last count as a byte */ for (i = 0; i < WS-1; i++) *v++ = 0; v -= i; printf("collapse %%d -> %%d\n", vsize, v - (char *)&comp_now); return v - (char *)&comp_now;#if !defined(NOCOMP)compress(char *vin, int n) /* default compression */ int delta = 0; s_hash((uchar *)vin, n); /* sets K1 and K2 */ if (S_A) { delta++; /* _a_t */ if (S_A > NFAIR) delta += NFAIR; /* _cnt[] */ memcpy((char *) &comp_now + delta, (char *) &K1, WS); delta += WS;#if HC>0 memcpy((char *) &comp_now + delta, (char *) &K2, HC); delta += HC; return delta; char *vv = vin; char *v = (char *) &comp_now; for (i = 0; i < n; i++, vv++) if (!Mask[i]) *v++ = *vv; printf("compress %%d -> %%d\n", n, v - (char *)&comp_now);#if defined(MA)#if !defined(onstack_now)int onstack_now(void) {}#if !defined(onstack_put)void onstack_put(void) {}#if !defined(onstack_zap)void onstack_zap(void) {}onstack_zap(void){ struct H_el *v, *w, *last = 0; struct H_el **tmp = H_tab; char *nv; int n, m; H_tab = S_Tab; nv = (char *) &comp_now; n = compress((char *)&now, vsize);#if defined(BITSTATE) && defined(LC) n = compact_stack((char *)&now, vsize); nv = (char *) &now; n = vsize;#if !defined(HC) && !(defined(BITSTATE) && defined(LC)) s_hash((uchar *)nv, n); H_tab = tmp; for (v = S_Tab[j1]; v; Zh++, last=v, v=v->nxt) { m = memcmp(&(v->state), nv, n); if (m == 0) goto Found; if (m < 0)/* NotFound: */ Uerror("stack out of wack - zap"); return;Found: ZAPS++; if (last) last->nxt = v->nxt; S_Tab[j1] = v->nxt; v->tagged = (unsigned) n;#if !defined(NOREDUCE) && !defined(SAFETY) v->proviso = 0; v->nxt = last = (struct H_el *) 0; for (w = Free_list; w; Fa++, last=w, w = w->nxt) { if ((int) w->tagged <= n) { if (last) { v->nxt = w; /* was: v->nxt = w->nxt; */ last->nxt = v; { v->nxt = Free_list; Free_list = v; if (!w->nxt) { w->nxt = v; Free_list = v;onstack_put(void){ struct H_el **tmp = H_tab; if (hstore((char *)&now, vsize) != 0) printf("pan: warning, double stack entry\n"); Uerror("cannot happen - unstack_put"); trpt->ostate = Lstate; PUT++;onstack_now(void){ struct H_el *tmp; struct H_el **tmp2 = H_tab; char *v; int n, m = 1; v = (char *) &comp_now; v = (char *) &now; H_tab = tmp2; for (tmp = S_Tab[j1]; tmp; Zn++, tmp = tmp->nxt) { m = memcmp(((char *)&(tmp->state)),v,n); if (m <= 0) { Lstate = (struct H_el *) tmp; PROBE++; return (m == 0);hinit(void) { void r_xpoint(void); r_xpoint(); dfa_init((unsigned short) (MA+a_cycles)); H_tab = (struct H_el **) emalloc((1L<= MA) { printf("pan: error, MA too small, recompile pan.c"); printf(" with -DMA=N with N>%%d\n", n); Uerror("aborting"); if (n > (int) maxgs) maxgs = (unsigned int) n; for (i = 0; i < n; i++) Info[i] = v[i]; for ( ; i < MA-1; i++) Info[i] = 0; Info[MA-1] = pbit; if (a_cycles) /* place _a_t at the end */ { Info[MA] = Info[0]; Info[0] = 0; } if (!dfa_store(Info)) { if (pbit == 0 && (now._a_t&1) && depth > A_depth) { Info[MA] &= ~(1|16|32); /* _a_t */ if (dfa_member(MA)) { Info[MA-1] = 4; /* off-stack bit */ nShadow++; if (!dfa_member(MA-1)) printf("intersected 1st dfs stack\n"); return 3; printf("new state\n"); return 0; /* new state */ if (pbit == 0) { Info[MA-1] = 1; /* proviso bit */ trpt->proviso = dfa_member(MA-1); Info[MA-1] = 4; /* off-stack bit */ if (dfa_member(MA-1)) { printf("old state\n"); return 1; /* off-stack */ } else { printf("on-stack\n"); return 2; /* on-stack */ printf("old state\n"); return 1; /* old state */compact_stack(char *vin, int n){ int delta = 0; delta++; /* room for state[0] |= 128 */ memcpy((char *) &comp_now + delta, (char *) &K2, WS); delta += WS; /* use all available bits */hstore(char *vin, int nin) /* hash table storage */{ struct H_el *tmp, *ntmp, *olst = (struct H_el *) 0; char *v; int n, m=0; uchar rem_a; { v = (char *) &comp_now; n = compact_stack(vin, nin); { v = vin; n = nin; v = vin; n = nin; #ifdef HC rem_a = now._a_t; now._a_t = 0; #endif now._a_t = rem_a; { v[0] = 0; /* _a_t */ for (m = 0; m < NFAIR; m++) v[m+1] = 0; /* _cnt[] */ m = 0; { tmp = grab_state(n); H_tab[j1] = tmp; { for (;; hcmp++, olst = tmp, tmp = tmp->nxt) { /* skip the _a_t and the _cnt bytes */ if (tmp->ln != 0) { if (!tmp->nxt) goto Append; m = memcmp(((char *)&(tmp->state)) + S_A, v + S_A, n - S_A); if (m == 0) {#define wasnew 0 int wasnew = 0; if (S_A) { if ((((char *)&(tmp->state))[0] & V_A) != V_A) { wasnew = 1; nShadow++; ((char *)&(tmp->state))[0] |= V_A; } if (S_A > NFAIR) { /* 0 <= now._cnt[now._a_t&1] < MAXPROC */ unsigned ci, bp; /* index, bit pos */ ci = (now._cnt[now._a_t&1] / 8); bp = (now._cnt[now._a_t&1] - 8*ci); if (now._a_t&1) /* use tail-bits in _cnt */ { ci = (NFAIR - 1) - ci; bp = 7 - bp; /* bp = 0..7 */ ci++; /* skip over _a_t */ bp = 1 << bp; /* the bit mask */ if ((((char *)&(tmp->state))[ci] & bp)==0) { if (!wasnew) { wasnew = 1; nShadow++; ((char *)&(tmp->state))[ci] |= bp; } /* else: wasnew == 0, i.e., old state */ if (wasnew) tmp->tagged |= V_A; if ((now._a_t&1) && (tmp->tagged&A_V) && depth > A_depth)intersect: printf("1st dfs-stack intersected on state %%d+\n", (int) tmp->st_id); return 3; printf(" New state %%d+\n", (int) tmp->st_id); dumpstate(1, (char *)&(tmp->state),n,tmp->tagged); if ((S_A)?(tmp->tagged&V_A):tmp->tagged) /* already on current dfs stack */ /* but may also be on 1st dfs stack */ && depth > A_depth && (!fairness || now._cnt[1] <= 1) ) goto intersect; printf(" Stack state %%d\n", (int) tmp->st_id); dumpstate(0, (char *)&(tmp->state),n,tmp->tagged); return 2; /* match on stack */ dumpstate(1, (char *)&(tmp->state), n, 0); printf(" Old state %%d\n", (int) tmp->st_id); dumpstate(0, (char *)&(tmp->state), n, 0);#ifdef REACH if (tmp->D > depth) { tmp->D = depth; printf(" ReVisiting (from smaller depth)\n"); nstates--;#if defined(BFS) && defined(Q_PROVISO) Lstate = (struct H_el *) tmp; return 1; /* match outside stack */ } else if (m < 0) { /* insert state before tmp */ ntmp = grab_state(n); ntmp->nxt = tmp; if (!olst) H_tab[j1] = ntmp; olst->nxt = ntmp; tmp = ntmp; } else if (!tmp->nxt) { /* append after tmp */Append: tmp->nxt = grab_state(n); tmp = tmp->nxt; } } tmp->st_id = (unsigned) nstates; printf(" Push state %%d\n", ((int) nstates) - 1); printf(" New state %%d\n", (int) nstates);#if !defined(SAFETY) || defined(REACH) tmp->D = depth; { v[0] = V_A; { unsigned ci, bp; /* as above */ if (now._a_t&1) v[1+ci] = 1 << bp; tmp->tagged = (S_A)?V_A:(depth+1); dumpstate(-1, v, n, tmp->tagged); Lstate = (struct H_el *) tmp; dumpstate(-1, v, n, 0);#include TRANSITIONSdo_reach(void)#if defined(BFS) && defined(REACH)#undef REACH#define BASE 1#define BASE 0typedef struct Trans { short atom; /* if &2 = atomic trans; if &8 local */ short escp[HAS_UNLESS]; /* lists the escape states */ short e_trans; /* if set, this is an escp-trans */ short tpe[2]; /* class of operation (for reduction) */ short qu[6]; /* for conditional selections: qid's */ uchar ty[6]; /* ditto: type's */ short om; /* completion status of preselects */ char *tp; /* src txt of statement */ int st; /* the nextstate */ int t_id; /* transition id, unique within proc */ int forw; /* index forward transition */ int back; /* index return transition */ struct Trans *nxt;} Trans; #define qptr(x) (((uchar *)&now)+(int)q_offset[x])#define pptr(x) (((uchar *)&now)+(int)proc_offset[x])extern uchar *Pptr(int);#define q_sz(x) (((Q0 *)qptr(x))->Qlen) #ifndef VECTORSZ#define VECTORSZ 1024 /* sv size in bytes */#ifndef CHECK#define CHECK#ifndef DEBUG#define DEBUG#define NOFAIR#ifdef NOREDUCE#define XUSAFE#if !defined(SAFETY) && !defined(MA)#define FULLSTACK#ifdef SAFETY && !defined(HASH64)#define CNTRSTACK#define NOCOMP#if !defined(LC) && defined(SC)#define LC#if defined(COLLAPSE2) || defined(COLLAPSE3) || defined(COLLAPSE4)/* accept the above for backward compatibility */#define COLLAPSE#undef HC#define HC4#ifdef HC0#define HC 0#ifdef HC1#define HC 1#ifdef HC2#define HC 2#ifdef HC3#define HC 3#ifdef HC4#define HC 4unsigned long ncomps[256+2];#define MAXQ 255#define MAXPROC 255#define WS sizeof(long) /* word size in bytes */typedef struct Stack { /* for queues and processes */ int o_delta; int o_offset; int o_skip; int o_delqs; short o_delta; short o_offset; short o_skip; short o_delqs; short o_boq; char *o_name; char *body; struct Stack *nxt; struct Stack *lst;} Stack; typedef struct Svtack { /* for complete state vector */ int m_delta; short o_delta; /* current size of frame */ short m_delta; /* maximum size of frame */ struct Svtack *nxt; struct Svtack *lst;} Svtack; Trans ***trans; /* 1 ptr per state per proctype */ #if defined(FULLSTACK) || defined(BFS)struct H_el *Lstate;int depthfound = -1; /* loop detection */int proc_offset[MAXPROC];int q_offset[MAXQ];short proc_offset[MAXPROC];short q_offset[MAXQ];uchar proc_skip[MAXPROC];uchar q_skip[MAXQ];unsigned long vsize; /* vector size in bytes */int vprefix=0, svfd; /* runtime option -pN */char *tprefix = "trail"; /* runtime option -tsuffix */short boq = -1; /* blocked_on_queue status */typedef struct State { uchar _nr_pr; uchar _nr_qs; uchar _a_t; /* cycle detection */ uchar _cnt[NFAIR]; /* counters, weak fairness */ unsigned short _vsz; unsigned long _vsz; uchar _last; /* pid executed in last step */#if nstates_event<256 uchar _event; unsigned short _event;){ int j, h = now._nr_pr; int k; uchar *o_this = this; if (TstOnly) return (h < MAXPROC);/* redefine Index only within this procedure */#undef Index#define Index(x, y) Boundcheck(x, y, 0, 0, 0) if (h >= MAXPROC) Uerror("too many processes"); switch (n) { case 0: j = sizeof(P0); break; default: Uerror("bad proc - addproc"); if (vsize%%WS) proc_skip[h] = WS-(vsize%%WS); proc_skip[h] = 0; for (k = vsize + (int) proc_skip[h]; k > vsize; k--) Mask[k-1] = 1; /* align */ vsize += (int) proc_skip[h]; proc_offset[h] = vsize; { int dummy = 0; write(svfd, (uchar *) &dummy, sizeof(int)); /* mark */ write(svfd, (uchar *) &h, sizeof(int)); write(svfd, (uchar *) &n, sizeof(int)); write(svfd, (uchar *) &proc_offset[h], sizeof(int)); write(svfd, (uchar *) &proc_offset[h], sizeof(short)); write(svfd, (uchar *) &now, vprefix-4*sizeof(int)); /* padd */ if (fairness && ((int) now._nr_pr + 1 >= (8*NFAIR)/2)) { printf("pan: error: too many processes -- current"); printf(" max is %%d procs (-DNFAIR=%%d)\n", (8*NFAIR)/2 - 2, NFAIR); printf("\trecompile with -DNFAIR=%%d\n", NFAIR+1); vsize += j; for (k = 1; k <= Air[n]; k++) Mask[vsize - k] = 1; /* pad */ Mask[vsize-j] = 1; /* _pid */ hmax = max(hmax, vsize); if (vsize >= VECTORSZ) { printf("pan: error, VECTORSZ too small, recompile pan.c"); printf(" with -DVECTORSZ=N with N>%%d\n", vsize); memset((char *)pptr(h), 0, j); ((P0 *)this)->_pid = h-BASE; ((P0 *)this)->_pid = h;addqueue(int n, int is_rv){ int j=0, i = now._nr_qs; if (i >= MAXQ) Uerror("too many queues"); default: Uerror("bad queue - addqueue"); q_skip[i] = WS-(vsize%%WS); q_skip[i] = 0; k = vsize; if (is_rv) k += j; for (k += (int) q_skip[i]; k > vsize; k--) Mask[k-1] = 1; vsize += (int) q_skip[i]; q_offset[i] = vsize; Uerror("VECTORSZ is too small, edit pan.h"); memset((char *)qptr(i), 0, j); ((Q0 *)qptr(i))->_t = n; return i+1;{ int j; uchar *z; #ifdef HAS_SORTED if (!into--) uerror("ref to uninitialized chan name (sending)"); if (into >= (int) now._nr_qs || into < 0) Uerror("qsend bad queue#"); z = qptr(into); j = ((Q0 *)qptr(into))->Qlen; switch (((Q0 *)qptr(into))->_t) { case 0: printf("queue %%d was deleted\n", into+1); default: Uerror("bad queue - qsend"); if (in_s_scope(into+1)) require('s', into);q_zero(int from){ if (!from--) { uerror("ref to uninitialized chan name (q_zero)"); switch(((Q0 *)qptr(from))->_t) { case 0: printf("queue %%d was deleted\n", from+1); Uerror("bad queue q-zero");not_RV(int from){ if (q_zero(from)) { printf("==>> a test of the contents of a rv "); printf("channel always returns FALSE\n"); uerror("error to poll rendezvous channel");setq_claim(int x, int m, char *s, int y, char *p){ if (x == 0) uerror("x[rs] claim on uninitialized channel"); if (x < 0 || x > MAXQ) Uerror("cannot happen setq_claim"); q_claim[x] |= m; p_name[y] = p; q_name[x] = s; if (m&2) q_S_check(x, y); if (m&1) q_R_check(x, y);short q_sender[MAXQ+1];q_S_check(int x, int who){ if (!q_sender[x]) { q_sender[x] = who+1; if (q_zero(x)) { printf("chan %%s (%%d), ", q_name[x], x-1); printf("sndr proc %%s (%%d)\n", p_name[who], who); uerror("xs chans cannot be used for rv"); if (q_sender[x] != who+1) { printf("pan: xs assertion violated: "); printf("access to chan <%%s> (%%d)\npan: by ", q_name[x], x-1); if (q_sender[x] > 0 && p_name[q_sender[x]-1]) printf("%%s (proc %%d) and by ", p_name[q_sender[x]-1], q_sender[x]-1); printf("%%s (proc %%d)\n", p_name[who], who); uerror("error, partial order reduction invalid");short q_recver[MAXQ+1];q_R_check(int x, int who){ if (!q_recver[x]) { q_recver[x] = who+1; printf("recv proc %%s (%%d)\n", uerror("xr chans cannot be used for rv"); if (q_recver[x] != who+1) { printf("pan: xr assertion violated: "); printf("access to chan %%s (%%d)\npan: ", if (q_recver[x] > 0 && p_name[q_recver[x]-1]) printf("by %%s (proc %%d) and ", p_name[q_recver[x]-1], q_recver[x]-1); printf("by %%s (proc %%d)\n",q_len(int x){ if (!x--) uerror("ref to uninitialized chan name (len)"); return ((Q0 *)qptr(x))->Qlen;q_full(int from) uerror("ref to uninitialized chan name (qfull)"); Uerror("bad queue - q_full");q_e_f(int from){ /* empty or full */ return !q_len(from) || q_full(from);#if NQS>0qrecv(int from, int slot, int fld, int done){ uchar *z; int j, k, r=0; if (!from--) uerror("ref to uninitialized chan name (receiving)"); if (from >= (int) now._nr_qs || from < 0) Uerror("qrecv bad queue#"); z = qptr(from); if (done && (in_r_scope(from+1))) require('r', from); switch (((Q0 *)qptr(from))->_t) { default: Uerror("bad queue - qrecv"); return r;longcol_q(int i, char *z){ int j=0, k; char *x, *y; Q0 *ptr = (Q0 *) qptr(i); switch (ptr->_t) {run(void){ /* int i; */ memset((char *)&now, 0, sizeof(State)); vsize = (unsigned long) (sizeof(State) - VECTORSZ);/* optional provisioning statements, e.g. to *//* set hidden variables, used as constants */#ifdef PROV#include PROV settable(); Maxbody = max(Maxbody, sizeof(P%d)); reached[%d] = reached%d; accpstate[%d] = (uchar *) emalloc(nstates%d); progstate[%d] = (uchar *) emalloc(nstates%d); stopstate[%d] = (uchar *) emalloc(nstates%d); visstate[%d] = (uchar *) emalloc(nstates%d); mapstate[%d] = (short *) emalloc(nstates%d * sizeof(short)); NrStates[%d] = nstates%d; stopstate[%d][endstate%d] = 1; retrans(%d, nstates%d, start%d, src_ln%d, reached%d); if (state_tables) { printf("\nTransition Type: "); printf("A=atomic; D=d_step; L=local; G=global\n"); printf("Source-State Labels: "); printf("p=progress; e=end; a=accept;\n"); printf("Note: statement merging was used. Only the first\n"); printf(" stmnt executed in each merge sequence is shown\n"); printf(" (use spin -a -o3 to disable statement merging)\n"); pan_exit(0);#define ACCEPT_LAB 1 /* at least 1 in np_ */#define ACCEPT_LAB %d /* user-defined accept labels */#define PROG_LAB %d /* progress labels */uchar *accpstate[%d];uchar *progstate[%d];uchar *reached[%d];uchar *stopstate[%d];uchar *visstate[%d];short *mapstate[%d];int NrStates[%d]; Maxbody = max(Maxbody, sizeof(Q%d)); r_ck(reached%d, nstates%d, %d, src_ln%d, src_file%d); case %d: j = sizeof(P%d); break; this = o_this; return h-BASE;#define Index(x, y) Boundcheck(x, y, II, tt, t)#if defined(BITSTATE) && defined(COLLAPSE)/* just to allow compilation, to generate the error */long col_p(int i, char *z) { return 0; }long col_q(int i, char *z) { return 0; }col_p(int i, char *z){ int j, k; unsigned long ordinal(char *, long, short); P0 *ptr = (P0 *) pptr(i); default: Uerror("bad proctype - collapse"); if (z) x = z; else x = scratch; y = (char *) ptr; k = proc_offset[i]; for ( ; j > 0; j--, y++) if (!Mask[k++]) *x++ = *y; x -= j; if (z) return (long) (x - z); return ordinal(scratch, x-scratch, (short) (2+ptr->_t)); default: Uerror("bad qtype - collapse"); y = (char *) ptr; k = q_offset[i]; /* no need to store the empty slots at the end */ j -= (q_max[ptr->_t] - ptr->Qlen) * ((j - 2)/q_max[ptr->_t]); return ordinal(scratch, x-scratch, 1); /* chan */ case %d: r = ((Q%d *)z)->contents[slot].fld%d; break;int unsend(int into){ int _m=0, j; uchar *z; uerror("ref to uninitialized chan (unsend)"); j = ((Q0 *)z)->Qlen; ((Q0 *)z)->Qlen = --j; default: Uerror("bad queue - unsend");unrecv(int from, int slot, int fld, int fldvar, int strt) uerror("ref to uninitialized chan (unrecv)"); if (strt) ((Q0 *)z)->Qlen = j+1;/** function prototypes **/char *emalloc(unsigned long);char *Malloc(unsigned long);int Boundcheck(int, int, int, int, Trans *);int addqueue(int, int);/* int atoi(char *); *//* int abort(void); */int close(int);int delproc(int, int);int endstate(void);int hstore(char *, int);int gstore(char *, int, uchar);int q_cond(short, Trans *);int q_full(int);int q_len(int);int q_zero(int);int qrecv(int, int, int, int);int unsend(int);/* void *sbrk(int); */void Uerror(char *);void assert(int, char *, int, int, Trans *);void c_chandump(int);void c_globals(void);void c_locals(int, int);void checkcycles(void);void crack(int, int, Trans *, short *);void d_hash(uchar *, int);void s_hash(uchar *, int);void r_hash(uchar *, int);void delq(int);void do_reach(void);void pan_exit(int);void exit(int);void hinit(void);void imed(Trans *, int, int, int);void new_state(void);void p_restor(int);void putpeg(int, int);void putrail(void);void q_restor(void);void retrans(int, int, int, short *, uchar *);void settable(void);void setq_claim(int, int, char *, int, char *);void sv_restor(void);void sv_save(void);void tagtable(int, int, int, short *, uchar *);void uerror(char *);void unrecv(int, int, int, int, int);void usage(FILE *);void wrap_stats(void);int onstack_now(void);void onstack_init(void);void onstack_put(void);void onstack_zap(void);int q_S_check(int, int);int q_R_check(int, int);uchar q_claim[MAXQ+1];char *q_name[MAXQ+1];char *p_name[MAXPROC+1];to_compile(void){ char ctd[1024], carg[64]; strcpy(ctd, "-DBITSTATE "); strcpy(ctd, ""); strcat(ctd, "-DNOVSZ "); sprintf(carg, "-DMEMLIM=%%d ", MEMLIM); strcat(ctd, carg); sprintf(carg, "-DMEMCNT=%%d ", MEMCNT); strcat(ctd, "-DNOCLAIM "); strcat(ctd, "-DSAFETY ");#ifdef NOFAIR strcat(ctd, "-DNOFAIR ");#ifdef NFAIR if (NFAIR != 2) { sprintf(carg, "-DNFAIR=%%d ", NFAIR); strcat(ctd, carg); strcat(ctd, "-DNOREDUCE ");#ifdef XUSAFE strcat(ctd, "-DXUSAFE "); strcat(ctd, "-DNP "); strcat(ctd, "-DPEG "); strcat(ctd, "-DVAR_RANGES "); strcat(ctd, "-DHC0 "); strcat(ctd, "-DHC1 "); strcat(ctd, "-DHC2 "); strcat(ctd, "-DHC3 "); strcat(ctd, "-DHC4 "); strcat(ctd, "-DCHECK "); strcat(ctd, "-DCTL "); strcat(ctd, "-DNIBIS ");#ifdef NOBOUNDCHECK strcat(ctd, "-DNOBOUNDCHECK ");#ifdef NOSTUTTER strcat(ctd, "-DNOSTUTTER "); strcat(ctd, "-DREACH "); strcat(ctd, "-DPRINTF "); strcat(ctd, "-DOTIM "); strcat(ctd, "-DCOLLAPSE "); sprintf(carg, "-DMA=%%d ", MA); strcat(ctd, "-DSVDUMP ");#ifdef VECTORSZ if (VECTORSZ != 1024) { sprintf(carg, "-DVECTORSZ=%%d ", VECTORSZ); strcat(ctd, "-DVERBOSE "); strcat(ctd, "-DSDUMP "); strcat(ctd, "-DCOVEST "); printf("Compiled as: cc -o pan %%span.c\n", ctd); "%s", #define SYNC %d #define ASYNC %d short Air[] = { ,%s (short) Air%d, (short) Air%d }; char *procname[] = { ":np_:", }; np_ uchar sv[VECTORSZ]; } State; #define HAS_TRACK %d int addproc(int n, int par%d int provided(int II, unsigned char ot, int tt, Trans *t) { switch(ot) { default: return 1; /* e.g., a claim */ } return 0; } if (state_tables) ini_claim(%d, 0); iniglobals(); } void iniglobals(void) { #ifdef VAR_RANGES logval(" Maxbody = max(Maxbody, sizeof(State)-VECTORSZ); } endstopstateprogressprogstateacceptaccpstate %s[%d][%d] = 1; %s label inside d_step%s label inside atomic-spin: %3d:%s, warning, %s - is invisible visstate[%d][%d] = 1; spin: warning, line %3d %s, proctype %s:global '%s %s' could be declared 'bit %s' '%s %s' could be declared 'byte %s' ((P%d *)pptr(h))->; = %s%s:", ((P%d *)pptr(h))->); :never:error: %s defines local %s void c_chandump(int unused) { unused = unused++; /* avoid complaints */ } void c_chandump(int from) { uchar *z; int slot; from--; if (from >= (int) now._nr_qs || from < 0) { printf("pan: bad qid %%d\n", from+1); return; } z = qptr(from); switch (((Q0 *)z)->_t) { case %d: ((Q%d *)z)->for (slot = 0; slot < %sQlen; slot++) { printf(" ["); printm(%scontents[slot].fld%d); printf("%%d,", %scontents[slot].fld%d); printf("],"); } break; printf("\n"); } printf(" (struct %s)\n"); %s%s. printf(" %s %s: %%d\n", %s%s); { int l_in; for (l_in = 0; l_in < %d; l_in++) { printf(" %s %s[%%d]: %%d\n", l_in, %s%s[l_in]); } printf(" chan %s (=%%d): len %%d:\t", %s%s, q_len(%s%s)); c_chandump(%s%s); printf(" chan %s[%d] (=%%d): len %%d:\t", %s%s[%d], q_len(%s%s[%d])); c_chandump(%s%s[%d]); :trace::notrace:((P%d *)pptr(pid))->void c_globals(void) { /* int i; */ printf("global vars:\n"); now.void c_locals(int pid, int tp) { /* int i; */ switch(tp) { case %d: printf("local vars proc %%d (%s):\n", pid); /* none */ break; } } void printm(int x) { switch (x) { case %d: Printf("%s"); break; default: Printf("%%d", x); ", now.cannot hide non-globals (%s)cannot hide channels (%s)/* hidden variable: */int _; /* a predefined write-only variable */ %s%s%s%s%s%s%s %s%s%s[%d]%s%s%s[%d] %s%s%s[l_in]%s%s%s[l_in]addqueue(%d, %d)%d:init:#define Pinit ((P%d *)this) _:never_template:_#define P%s ((P%d *)this) typedef struct P%d { /* %s */ unsigned _pid : 8; /* 0..255 */ unsigned _t : %d; /* proctype */ unsigned _p : %d; /* state */ } P%d; #define Air%d 0 #define Air%d (sizeof(P%d) - Offsetof(P%d, %s) - %d*sizeof(uchar)short)int)cannot happen Air %s) #define _NP_ %d uchar reached%d[3]; /* np_ */ #define nstates%d 3 /* np_ */ #define endstate%d 2 /* np_ */ #define start%d 0 /* np_ */ case %d: /* np_ */ ini_claim(%d, h); ((P%d *)pptr(h))->_t = %d; ((P%d *)pptr(h))->_p = 0; reached%d[0] = 1; accpstate[%d][1] = 1; case %d: /* %s */ #define start%d %d #define start_claim %d #define start_event %d ((P%d *)pptr(h))->_p = %d; reached%d[%d]=1; case %d: /* %s */ if () return 1; /* params: */ array in parameter list, %s ((P%d *)pptr(h))->hidden array in parameter %s = par%d; /* locals: */ #ifdef HAS_CODE locinit%d(h); confusing control structure uchar %s; unsigned %s : %d unsigned %s : 1spin: warning: bit-array %s[%d] mapped to byte-array uchar %s short %s int %sundeclared structure element %s struct %s %svariable %s undeclared[%d] ushortuint Qlen; /* q_size */ #define NQS 1 /* nqs=%d, but has_io */ #define NQS %d short q_flds[%d]; short q_max[%d]; case %d: j = sizeof(Q%d); q_flds[%d] = %d; q_max[%d] = %d; break; typedef struct Q%d { uchar _t; /* q_type */ struct { unsigned fld%d : 1; uchar fld%d; short fld%d; int fld%d; bad channel spec } contents[%d]; } Q%d; typedef struct Q0 { /* generic q */ uchar _t; } Q0; int Q_has(int, int, intint Q_has(int into, int want%d, int fld%d{ int i; if (!into--) uerror("ref to unknown chan (recv-poll)"); if (into >= now._nr_qs || into < 0) Uerror("qrecv bad queue#"); for (i = 0; i < ((Q0 *)qptr(into))->Qlen; i++) { if (want%d && qrecv(into+1, i, %d, 0) != fld%d) continue; return i+1; return 0; #if NQS>0 void qsend(int into, int sorted, int fld%d /* =rv= */ case %d:%s (trpt+2)->o_m = 0; if (!sorted) goto append%d; for (j = 0; j < %sQlen; j++) { /* find insertion point */ ((Q%d *)z)->contents[j].fld if (fld%d > %s%d) continue; if (fld%d < %s%d) goto found%d; found%d: for (k = %sQlen - 1; k >= j; k--) { /* shift up */ %scontents[k+1].fld%d = %scontents[k].fld%d; append%d: /* insert in slot j */ #ifdef HAS_SORTED (trpt+1)->ipt = j; %sQlen = %sQlen + 1; %s%d = fld%d; case %d: return %d; case %d: return (q_sz(from) == %d); case %d:%s if (fld == 0) r = %scontents[slot].fld0; switch (fld) { default: Uerror("too many fields in recv"); if (done) { j = %sQlen - 1; %sQlen = 0; ((Q%d *)z)->contents { j = %sQlen; %sQlen = --j; for (k=slot; kV2Vk@(Vk@Vk@VUk@Uk@UUk@Uk@UUk@Uk@Uk@U}Uk@sUk@mUaUk@GUk@AU5Uk@Uk@UTk@T`k@Tk@TTk@Tk@sTgTk@]Tk@WTKTk@ATk@;T/Tk@%T k@TTk@ Tk@SSk@S׳k@SSk@Sѳk@wSkSk@aSk@GS;Sk@1Sk@RRRk@RRk@Rk@RRk@Rk@RRk@R{k@wRkRk@aRjk@LR:RRk@'RRk@RBk@RQk@Q-k@QQk@Q k@QQk@Qk@QQk@Qk@{QoQk@eQk@_QSQk@'Q$k@!QQk@ Qk@QPk@Pʲk@PPk@Pk@PPk@Pk@yPLk@kPk@YPGP3k@Pk@P Pk@O`k@OOk@Ok@oOk@iO]Ok@COk@,O Ok@OUk@Nk@NNk@N`k@NNk@~Nk@mNaNk@WNDk@NNk@MMk@M,k@MMk@M+k@MMk@Mk@M}Mk@sMk@mMaMk@WMk@DM8Mk@.Mk@MMk@Mk@LLk@Lk@LLk@Lk@LxLk@nL`k@^LLL3k@9L-Lk@#LFk@LLk@Kk@KKk@K6k@KKk@K k@KwKk@mKk@)KKk@KJk@Jk@JJk@Jk@JJk@Jk@Jk@J{Jk@qJek@_JSJk@IJXk@&JLk@Jk@JI3k@Ik@IIk@I k@IIk@Ik@pIdIk@ZI@k@>n;>yn;>>n;>n;>>nn;>n;>>n;v>`n;[>S>@n;4>n;.>">n;>*n;=n;==n;= n;=n;==n;=n;= n;= n;=~=n;Z=n;>= n;3=n;-=!=n;=n;< n;< n;< n;< n;< n;< n;r< n;g<n;a<U<n;K<n;0<$<n;<n;j;5 L;D;9:::95 9909,95 9 92928828828+28828q28828`28s82i8+2c8W82M82/8#8282 872727727O27727D2u7i72_7 2K7C7'2'7ĸ27ȸ2 772662626626ĸ2}6ȸ2662 6265ظ25255ظ25ڪ255ظ25Ԫ255ظ25v5ظ2l5Ϫ2]5Q5ظ2G52%5ܸ2552 52442424424ȩ2442412u4i42_4q2I42C4742-4Y24и24423E23323и2332323u32k32^3R32H312+323и225 221212212122121y2m21c21V2J21@2ȩ1'221211111111111111111`1111x1@1k1_11U1 1H1<1121 11115 10+0+00+0+00+0+00+0+00+v0ߨ+n0b0+X0i+60 +(0+00+0i+/ +k/+e/Y/+O/+:/++/+/+ /+.+..+.i+. +..+.+.s.+i.+T.+C.+=.1.+'.+..+--+-+--- +-+--+-`+z-o-c-+Y- +O-D-8-+.-+(--+-+,,+,+,,B+,,+,,l+,v,ɤ+h,Y,+K,<,+6,*,+ ,s+,,l++5 +++i+p+a+X+=++"++5 **'**'** '**w*M'[*L*;'(**'**'))a')) ')))2'r)c)#'(( '((('(('K(('5 ''&'&x'm'a'&W'&Q'I'&0'('&&&&&&5 |&p&$Y&A$N&$/&$%&|$&y$&%%$%$%}$%$%$K%2%$ %$$$$5 $$}"$$"$s$`"\$M$@"$"$$#"## "##"##"##"##u#"`#U#F#"5#&#"#""""""`"""}"""A""D"">"/"%")""""5 !!!Ӥ !!1! #!!ɤ !    5 ]   ɤ5 w?WH?`?=?(?j[?>/?)????a?@?M/:??;5 !  qb i@3&q k\VGA2,aJ/Ġ5 C=5 |yffTN</ z9|yfy.5 @fX/n`7P5 ԟPZRğPL5 %Ÿ5 sĸfȸUI?!ȸhĸĸcĸNȸH6Q :  s mgaUK(0    q`Qи@1и$ĸȸ5   5       v ] ̸S (M A 7 +1 )         }   w   s  o e 0_ S 9 j3 '  @_   V   c      u i Z P J > 2 #  Ԭ            y Nk иe Y O :I = , и     и    и и  и^ M &   ` и`v`иV`PD* ии`и5 RPL5 7+`` ``8```8```n@`h\ظ`R)`L@ظ`6`(ܸ`Ը``Ը``ظ`ܝ`ظ`ɝ`}ظ`s`eܸ`_S`9``3'``8```````{~`i`\5 H<\6*\ h\\\d\\\\\F\\\\\|p\V\PD\*\$\\`\\\\B\\\x\gE\4\\ \=\\0\\\\\\\\cW\M\=\2\#\\\\\\Μ\\\\\wk\^\X5 E9 / 5 [[[[[[d[`[\[X[T[P[L[H[D[@[<[8[4[0[,[([$[ [[[[[ [[[[ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ|ZxZtZpZlZhZdZ`Z\ZXZTZPZLZHZDZ@Z>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>|>x>t>p>l>h>d>`>\>X>T>P>L>H>D>@><>8>4>0>,>(>$> >>>>> >>>>================================|=x=t=p=l=h=d=`=\=X=T=P=L=H=D=@=<=8=4=0=,=(=$= ===== ====<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<|<x<t<p<l<h<d<`<\<X<T<P<L<H<D<@<<<8<4<0<,<(<$< <<<<< <<<<;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;|;x;t;p;l;h;d;`;\;X;T;P;L;H;D;@;<;8;4;0;,;(;$; ;;;;; ;;;;::::::::::::::::::::::::::::::::|:x:t:p:l:h:d:`:\:X:T:P:L:H:D:@:<:8:4:0:,:(:$: ::::: ::::99999999999999999999999999999999|9x9t9p9l9h9d9`9\9X9T9P9L9H9D9@9<9894909,9(9$9 99999 999988888888888888888888888888888888|8x8t8p8l8h8d8`8\8X8T8P8L8H8D8@8<8884808,8(8$8 88888 888877777777777777777777777777777777|7x7t7p7l7h7d7`7\7X7T7P7L7H7D7@7<7874707,7(7$7 77777 777766666666666666666666666666666666|6x6t6p6l6h6d6`6\6X6T6P6L6H6D6@6<6864606,6(6$6 66666 666655555555555555555555555555555555|5x5t5p5l5h5d5`5\5X5T5P5L5H5D5@5<5854505,5(5$5 55555 555544444444444444444444444444444444|4x4t4p4l4h4d4`4\4X4T4P4L4H4D4@4<4844404,4(4$4 44444 444433333333333333333333333333333333|3x3t3p3l3h3d3`3\3X3T3P3L3H3D3@3<3834303,3(3$3 33333 333322222222222222222222222222222222|2x2t2p2l2h2d2`2\2X2T2P2L2H2D2@2<2824202,2(2$2 22222 222211111111111111111111111111111111|1x1t1p1l1h1d1`1\1X1T1P1L1H1D1@1<1814101,1(1$1 11111 111100000000000000000000000000000000|0x0t0p0l0h0d0`0\0X0T0P0L0H0D0@0<0804000,0(0$0 00000 0000////////////////////////////////|/x/t/p/l/h/d/`/\/X/T/P/L/H/D/@/