summaryrefslogtreecommitdiff
path: root/sys/src/cmd/spin/pangen2.c
diff options
context:
space:
mode:
authorcinap_lenrek <cinap_lenrek@felloff.net>2017-11-22 21:09:31 +0100
committercinap_lenrek <cinap_lenrek@felloff.net>2017-11-22 21:09:31 +0100
commit28e9566dc539244b3b429c21c556d656733839c2 (patch)
tree1564ecdf009d240cb9247a10a0fcb6491e0424c4 /sys/src/cmd/spin/pangen2.c
parent077e719dfbf9bf2582bed80026251cc0d108c16e (diff)
spin: Update to most recent version. (thanks Ori_B)
from Ori_B: There were a small number of changes needed from the tarball on spinroot.org: - The mkfile needed to be updated - Memory.h needed to not be included - It needed to invoke /bin/cpp instead of gcc -E - It depended on `yychar`, which our yacc doesn't provide. I'm still figuring out how to use spin, but it seems to do the right thing when testing a few of the examples: % cd $home/src/Spin/Examples/ % spin -a peterson.pml % pcc pan.c -D_POSIX_SOURCE % ./6.out (Spin Version 6.4.7 -- 19 August 2017) + Partial Order Reduction Full statespace search for: never claim - (none specified) assertion violations + acceptance cycles - (not selected) invalid end states + State-vector 32 byte, depth reached 24, errors: 0 40 states, stored 27 states, matched 67 transitions (= stored+matched) 0 atomic steps hash conflicts: 0 (resolved) Stats on memory usage (in Megabytes): 0.002 equivalent memory usage for states (stored*(State-vector + overhead)) 0.292 actual memory usage for states 128.000 memory used for hash table (-w24) 0.534 memory used for DFS stack (-m10000) 128.730 total actual memory usage unreached in proctype user /tmp/Spin/Examples/peterson.pml:20, state 10, "-end-" (1 of 10 states) pan: elapsed time 1.25 seconds pan: rate 32 states/second
Diffstat (limited to 'sys/src/cmd/spin/pangen2.c')
-rw-r--r--sys/src/cmd/spin/pangen2.c1072
1 files changed, 752 insertions, 320 deletions
diff --git a/sys/src/cmd/spin/pangen2.c b/sys/src/cmd/spin/pangen2.c
index 05ad9fa1f..828ded881 100644
--- a/sys/src/cmd/spin/pangen2.c
+++ b/sys/src/cmd/spin/pangen2.c
@@ -1,13 +1,10 @@
/***** spin: pangen2.c *****/
-/* Copyright (c) 1989-2003 by Lucent Technologies, Bell Laboratories. */
-/* All Rights Reserved. This software is for educational purposes only. */
-/* No guarantee whatsoever is expressed or implied by the distribution of */
-/* this code. Permission is given to distribute this code provided that */
-/* this introductory message is not removed and no monies are exchanged. */
-/* Software written by Gerard J. Holzmann. For tool documentation see: */
-/* http://spinroot.com/ */
-/* Send all bug-reports and/or questions to: bugs@spinroot.com */
+/*
+ * This file is part of the public release of Spin. It is subject to the
+ * terms in the LICENSE file that is included in this source directory.
+ * Tool documentation is available at http://spinroot.com
+ */
#include "spin.h"
#include "version.h"
@@ -15,33 +12,40 @@
#include "pangen2.h"
#include "pangen4.h"
#include "pangen5.h"
+#include "pangen7.h"
#define DELTA 500 /* sets an upperbound on nr of chan names */
#define blurb(fd, e) { fprintf(fd, "\n"); if (!merger) fprintf(fd, "\t\t/* %s:%d */\n", \
e->n->fn->name, e->n->ln); }
-#define tr_map(m, e) { if (!merger) fprintf(tt, "\t\ttr_2_src(%d, %s, %d);\n", \
+#define tr_map(m, e) { if (!merger) fprintf(tt, "\t\ttr_2_src(%d, \"%s\", %d);\n", \
m, e->n->fn->name, e->n->ln); }
extern ProcList *rdy;
extern RunList *run;
+extern Lextok *runstmnts;
extern Symbol *Fname, *oFname, *context;
extern char *claimproc, *eventmap;
-extern int lineno, verbose, Npars, Mpars;
+extern int lineno, verbose, Npars, Mpars, nclaims;
extern int m_loss, has_remote, has_remvar, merger, rvopt, separate;
-extern int Ntimeouts, Etimeouts, deadvar;
-extern int u_sync, u_async, nrRdy;
+extern int Ntimeouts, Etimeouts, deadvar, old_scope_rules, old_priority_rules;
+extern int u_sync, u_async, nrRdy, Unique;
extern int GenCode, IsGuard, Level, TestOnly;
+extern int globmin, globmax, ltl_mode, dont_simplify;
+
extern short has_stack;
-extern char *NextLab[];
+extern char *NextLab[64]; /* must match value in dstep.c:18 */
-FILE *tc, *th, *tt, *tm, *tb;
+int buzzed;
+FILE *tc, *th, *tt, *tb;
+static FILE *tm;
-int OkBreak = -1;
+int OkBreak = -1, has_hidden = 0; /* has_hidden set in sym.c and structs.c */
short nocast=0; /* to turn off casts in lvalues */
short terse=0; /* terse printing of varnames */
short no_arrays=0;
short has_last=0; /* spec refers to _last */
+short has_priority=0; /* spec refers to _priority */
short has_badelse=0; /* spec contains else combined with chan refs */
short has_enabled=0; /* spec contains enabled() */
short has_pcvalue=0; /* spec contains pc_value() */
@@ -52,9 +56,7 @@ short has_xu=0; /* spec contains xr or xs assertions */
short has_unless=0; /* spec contains unless statements */
short has_provided=0; /* spec contains PROVIDED clauses on procs */
short has_code=0; /* spec contains c_code, c_expr, c_state */
-short _isok=0; /* checks usage of predefined variable _ */
-short evalindex=0; /* evaluate index of var names */
-short withprocname=0; /* prefix local varnames with procname */
+short has_ltl=0; /* has inline ltl formulae */
int mst=0; /* max nr of state/process */
int claimnr = -1; /* claim process, if any */
int eventmapnr = -1; /* event trace, if any */
@@ -74,6 +76,9 @@ static int TPE[2], EPT[2];
static int uniq=1;
static int multi_needed, multi_undo;
static short AllGlobal=0; /* set if process has provided clause */
+static short withprocname=0; /* prefix local varnames with procname */
+static short _isok=0; /* checks usage of predefined variable _ */
+static short evalindex=0; /* evaluate index of var names */
int has_global(Lextok *);
static int getweight(Lextok *);
@@ -86,6 +91,29 @@ static void putproc(ProcList *);
static void Tpe(Lextok *);
extern void spit_recvs(FILE *, FILE*);
+static L_List *keep_track;
+
+void
+keep_track_off(Lextok *n)
+{ L_List *p;
+
+ p = (L_List *) emalloc(sizeof(L_List));
+ p->n = n;
+ p->nxt = keep_track;
+ keep_track = p;
+}
+
+int
+check_track(Lextok *n)
+{ L_List *p;
+
+ for (p = keep_track; p; p = p->nxt)
+ { if (p->n == n)
+ { return n->sym?n->sym->type:0;
+ } }
+ return 0;
+}
+
static int
fproc(char *s)
{ ProcList *p;
@@ -98,12 +126,33 @@ fproc(char *s)
return -1;
}
+int
+pid_is_claim(int p) /* Pid (p->tn) to type (p->b) */
+{ ProcList *r;
+
+ for (r = rdy; r; r = r->nxt)
+ { if (r->tn == p) return (r->b == N_CLAIM);
+ }
+ printf("spin: error, cannot find pid %d\n", p);
+ return 0;
+}
+
static void
reverse_procs(RunList *q)
{
if (!q) return;
reverse_procs(q->nxt);
- fprintf(tc, " Addproc(%d);\n", q->tn);
+ fprintf(tc, " Addproc(%d, %d);\n",
+ q->tn, q->priority < 1 ? 1 : q->priority);
+}
+
+static void
+forward_procs(RunList *q)
+{
+ if (!q) return;
+ fprintf(tc, " Addproc(%d, %d);\n",
+ q->tn, q->priority < 1 ? 1 : q->priority);
+ forward_procs(q->nxt);
}
static void
@@ -111,13 +160,14 @@ tm_predef_np(void)
{
fprintf(th, "#define _T5 %d\n", uniq++);
fprintf(th, "#define _T2 %d\n", uniq++);
+
fprintf(tm, "\tcase _T5:\t/* np_ */\n");
if (separate == 2)
- fprintf(tm, "\t\tif (!((!(o_pm&4) && !(tau&128))))\n");
- else
- fprintf(tm, "\t\tif (!((!(trpt->o_pm&4) && !(trpt->tau&128))))\n");
-
+ { fprintf(tm, "\t\tif (!((!(o_pm&4) && !(tau&128))))\n");
+ } else
+ { fprintf(tm, "\t\tif (!((!(trpt->o_pm&4) && !(trpt->tau&128))))\n");
+ }
fprintf(tm, "\t\t\tcontinue;\n");
fprintf(tm, "\t\t/* else fall through */\n");
fprintf(tm, "\tcase _T2:\t/* true */\n");
@@ -151,51 +201,120 @@ static struct {
void
gensrc(void)
{ ProcList *p;
+ int i;
+
+ disambiguate(); /* avoid name-clashes between scopes */
- if (!(tc = fopen(Cfile[0].nm[separate], "w")) /* main routines */
- || !(th = fopen(Cfile[1].nm[separate], "w")) /* header file */
- || !(tt = fopen(Cfile[2].nm[separate], "w")) /* transition matrix */
- || !(tm = fopen(Cfile[3].nm[separate], "w")) /* forward moves */
- || !(tb = fopen(Cfile[4].nm[separate], "w"))) /* backward moves */
+ if (!(tc = fopen(Cfile[0].nm[separate], MFLAGS)) /* main routines */
+ || !(th = fopen(Cfile[1].nm[separate], MFLAGS)) /* header file */
+ || !(tt = fopen(Cfile[2].nm[separate], MFLAGS)) /* transition matrix */
+ || !(tm = fopen(Cfile[3].nm[separate], MFLAGS)) /* forward moves */
+ || !(tb = fopen(Cfile[4].nm[separate], MFLAGS))) /* backward moves */
{ printf("spin: cannot create pan.[chtmfb]\n");
alldone(1);
}
- fprintf(th, "#define Version \"%s\"\n", Version);
- fprintf(th, "#define Source \"%s\"\n\n", oFname->name);
- if (separate != 2)
- fprintf(th, "char *TrailFile = Source; /* default */\n");
+ fprintf(th, "#ifndef PAN_H\n");
+ fprintf(th, "#define PAN_H\n\n");
+
+ fprintf(th, "#define SpinVersion \"%s\"\n", SpinVersion);
+ fprintf(th, "#define PanSource \"");
+ for (i = 0; oFname->name[i] != '\0'; i++)
+ { char c = oFname->name[i];
+ if (c == '\\' || c == ' ') /* Windows path */
+ { fprintf(th, "\\");
+ }
+ fprintf(th, "%c", c);
+ }
+ fprintf(th, "\"\n\n");
+
+ fprintf(th, "#define G_long %d\n", (int) sizeof(long));
+ fprintf(th, "#define G_int %d\n\n", (int) sizeof(int));
+ fprintf(th, "#define ulong unsigned long\n");
+ fprintf(th, "#define ushort unsigned short\n");
+
+ fprintf(th, "#ifdef WIN64\n");
+ fprintf(th, " #define ONE_L (1L)\n");
+ fprintf(th, "/* #define long long long */\n");
+ fprintf(th, "#else\n");
+ fprintf(th, " #define ONE_L (1L)\n");
+ fprintf(th, "#endif\n\n");
+
+ fprintf(th, "#ifdef BFS_PAR\n");
+ fprintf(th, " #define NRUNS %d\n", (runstmnts)?1:0);
+ fprintf(th, " #ifndef BFS\n");
+ fprintf(th, " #define BFS\n");
+ fprintf(th, " #endif\n");
+ fprintf(th, " #ifndef PUTPID\n");
+ fprintf(th, " #define PUTPID\n");
+ fprintf(th, " #endif\n\n");
+ fprintf(th, " #if !defined(USE_TDH) && !defined(NO_TDH)\n");
+ fprintf(th, " #define USE_TDH\n");
+ fprintf(th, " #endif\n");
+ fprintf(th, " #if defined(USE_TDH) && !defined(NO_HC)\n");
+ fprintf(th, " #define HC /* default for USE_TDH */\n");
+ fprintf(th, " #endif\n");
+ fprintf(th, " #ifndef BFS_MAXPROCS\n");
+ fprintf(th, " #define BFS_MAXPROCS 64 /* max nr of cores to use */\n");
+ fprintf(th, " #endif\n");
+
+ fprintf(th, " #define BFS_GLOB 0 /* global lock */\n");
+ fprintf(th, " #define BFS_ORD 1 /* used with -DCOLLAPSE */\n");
+ fprintf(th, " #define BFS_MEM 2 /* malloc from shared heap */\n");
+ fprintf(th, " #define BFS_PRINT 3 /* protect printfs */\n");
+ fprintf(th, " #define BFS_STATE 4 /* hashtable */\n\n");
+ fprintf(th, " #define BFS_INQ 2 /* state is in q */\n\n");
+
+ fprintf(th, " #ifdef BFS_FIFO\n"); /* queue access */
+ fprintf(th, " #define BFS_ID(a,b) (BFS_STATE + (int) ((a)*BFS_MAXPROCS+(b)))\n");
+ fprintf(th, " #define BFS_MAXLOCKS (BFS_STATE + (BFS_MAXPROCS*BFS_MAXPROCS))\n");
+ fprintf(th, " #else\n"); /* h_store access (not needed for o_store) */
+ fprintf(th, " #ifndef BFS_W\n");
+ fprintf(th, " #define BFS_W 10\n"); /* 1<<BFS_W locks */
+ fprintf(th, " #endif\n");
+ fprintf(th, " #define BFS_MASK ((1<<BFS_W) - 1)\n");
+ fprintf(th, " #define BFS_ID (BFS_STATE + (int) (j1_spin & (BFS_MASK)))\n");
+ fprintf(th, " #define BFS_MAXLOCKS (BFS_STATE + (1<<BFS_W))\n"); /* 4+1024 */
+ fprintf(th, " #endif\n");
+
+ fprintf(th, " #undef NCORE\n");
+ fprintf(th, " extern int Cores, who_am_i;\n");
+ fprintf(th, " #ifndef SAFETY\n");
+ fprintf(th, " #if !defined(BFS_STAGGER) && !defined(BFS_DISK)\n");
+ fprintf(th, " #define BFS_STAGGER 64 /* randomizer, was 16 */\n");
+ fprintf(th, " #endif\n");
+ fprintf(th, " #ifndef L_BOUND\n");
+ fprintf(th, " #define L_BOUND 10 /* default */\n");
+ fprintf(th, " #endif\n");
+ fprintf(th, " extern int L_bound;\n");
+ fprintf(th, " #endif\n");
+ fprintf(th, " #if defined(BFS_DISK) && defined(BFS_STAGGER)\n");
+ fprintf(th, " #error BFS_DISK and BFS_STAGGER are not compatible\n");
+ fprintf(th, " #endif\n");
+ fprintf(th, "#endif\n\n");
fprintf(th, "#if defined(BFS)\n");
- fprintf(th, "#ifndef SAFETY\n");
- fprintf(th, "#define SAFETY\n");
- fprintf(th, "#endif\n");
- fprintf(th, "#ifndef XUSAFE\n");
- fprintf(th, "#define XUSAFE\n");
- fprintf(th, "#endif\n");
+ fprintf(th, " #ifndef SAFETY\n");
+ fprintf(th, " #define SAFETY\n");
+ fprintf(th, " #endif\n");
+ fprintf(th, " #ifndef XUSAFE\n");
+ fprintf(th, " #define XUSAFE\n");
+ fprintf(th, " #endif\n");
fprintf(th, "#endif\n");
fprintf(th, "#ifndef uchar\n");
- fprintf(th, "#define uchar unsigned char\n");
+ fprintf(th, " #define uchar unsigned char\n");
fprintf(th, "#endif\n");
fprintf(th, "#ifndef uint\n");
- fprintf(th, "#define uint unsigned int\n");
+ fprintf(th, " #define uint unsigned int\n");
fprintf(th, "#endif\n");
- if (sizeof(void *) > 4) /* 64 bit machine */
- { fprintf(th, "#ifndef HASH32\n");
- fprintf(th, "#define HASH64\n");
- fprintf(th, "#endif\n");
- }
-#if 0
- if (sizeof(long)==sizeof(int))
- fprintf(th, "#define long int\n");
-#endif
if (separate == 1 && !claimproc)
{ Symbol *n = (Symbol *) emalloc(sizeof(Symbol));
Sequence *s = (Sequence *) emalloc(sizeof(Sequence));
+ s->minel = -1;
claimproc = n->name = "_:never_template:_";
- ready(n, ZN, s, 0, ZN);
+ ready(n, ZN, s, 0, ZN, N_CLAIM);
}
if (separate == 2)
{ if (has_remote)
@@ -207,20 +326,29 @@ gensrc(void)
fprintf(th, "#endif\n");
if (has_last)
fprintf(th, "#define HAS_LAST %d\n", has_last);
+ if (has_priority && !old_priority_rules)
+ fprintf(th, "#define HAS_PRIORITY %d\n", has_priority);
goto doless;
}
fprintf(th, "#define DELTA %d\n", DELTA);
fprintf(th, "#ifdef MA\n");
- fprintf(th, "#if MA==1\n"); /* user typed -DMA without size */
- fprintf(th, "#undef MA\n#define MA 100\n");
- fprintf(th, "#endif\n#endif\n");
+ fprintf(th, " #if NCORE>1 && !defined(SEP_STATE)\n");
+ fprintf(th, " #define SEP_STATE\n");
+ fprintf(th, " #endif\n");
+ fprintf(th, " #if MA==1\n"); /* user typed -DMA without size */
+ fprintf(th, " #undef MA\n");
+ fprintf(th, " #define MA 100\n");
+ fprintf(th, " #endif\n");
+ fprintf(th, "#endif\n");
fprintf(th, "#ifdef W_XPT\n");
- fprintf(th, "#if W_XPT==1\n"); /* user typed -DW_XPT without size */
- fprintf(th, "#undef W_XPT\n#define W_XPT 1000000\n");
- fprintf(th, "#endif\n#endif\n");
+ fprintf(th, " #if W_XPT==1\n"); /* user typed -DW_XPT without size */
+ fprintf(th, " #undef W_XPT\n");
+ fprintf(th, " #define W_XPT 1000000\n");
+ fprintf(th, " #endif\n");
+ fprintf(th, "#endif\n");
fprintf(th, "#ifndef NFAIR\n");
- fprintf(th, "#define NFAIR 2 /* must be >= 2 */\n");
+ fprintf(th, " #define NFAIR 2 /* must be >= 2 */\n");
fprintf(th, "#endif\n");
if (Ntimeouts)
fprintf(th, "#define NTIM %d\n", Ntimeouts);
@@ -230,18 +358,33 @@ gensrc(void)
fprintf(th, "#define REM_VARS 1\n");
if (has_remote)
fprintf(th, "#define REM_REFS %d\n", has_remote); /* not yet used */
+ if (has_hidden)
+ { fprintf(th, "#define HAS_HIDDEN %d\n", has_hidden);
+ fprintf(th, "#if defined(BFS_PAR) || defined(BFS)\n");
+ fprintf(th, " #error cannot use BFS on models with variables declared hidden\n");
+ fprintf(th, "#endif\n");
+ }
if (has_last)
fprintf(th, "#define HAS_LAST %d\n", has_last);
+ if (has_priority && !old_priority_rules)
+ fprintf(th, "#define HAS_PRIORITY %d\n", has_priority);
if (has_sorted)
fprintf(th, "#define HAS_SORTED %d\n", has_sorted);
if (m_loss)
fprintf(th, "#define M_LOSS\n");
if (has_random)
fprintf(th, "#define HAS_RANDOM %d\n", has_random);
- fprintf(th, "#define HAS_CODE\n"); /* doesn't seem to cause measurable overhead */
+ if (has_ltl)
+ fprintf(th, "#define HAS_LTL 1\n");
+ fprintf(th, "#define HAS_CODE 1\n"); /* could also be set to has_code */
+ /* always defining it doesn't seem to cause measurable overhead though */
+ /* and allows for pan -r etc to work for non-embedded code as well */
+ fprintf(th, "#if defined(RANDSTORE) && !defined(RANDSTOR)\n");
+ fprintf(th, " #define RANDSTOR RANDSTORE\n"); /* xspin uses RANDSTORE... */
+ fprintf(th, "#endif\n");
if (has_stack)
- fprintf(th, "#define HAS_STACK\n");
- if (has_enabled)
+ fprintf(th, "#define HAS_STACK %d\n", has_stack);
+ if (has_enabled || (has_priority && !old_priority_rules))
fprintf(th, "#define HAS_ENABLED 1\n");
if (has_unless)
fprintf(th, "#define HAS_UNLESS %d\n", has_unless);
@@ -252,11 +395,12 @@ gensrc(void)
if (has_badelse)
fprintf(th, "#define HAS_BADELSE %d\n", has_badelse);
if (has_enabled
+ || (has_priority && !old_priority_rules)
|| has_pcvalue
|| has_badelse
|| has_last)
{ fprintf(th, "#ifndef NOREDUCE\n");
- fprintf(th, "#define NOREDUCE 1\n");
+ fprintf(th, " #define NOREDUCE 1\n");
fprintf(th, "#endif\n");
}
if (has_np)
@@ -265,33 +409,46 @@ gensrc(void)
fprintf(th, "#define MERGED 1\n");
doless:
- fprintf(th, "#ifdef NP /* includes np_ demon */\n");
+ fprintf(th, "#if !defined(HAS_LAST) && defined(BCS)\n");
+ fprintf(th, " #define HAS_LAST 1 /* use it, but */\n");
+ fprintf(th, " #ifndef STORE_LAST\n"); /* unless the user insists */
+ fprintf(th, " #define NO_LAST 1 /* dont store it */\n");
+ fprintf(th, " #endif\n");
+ fprintf(th, "#endif\n");
+
+ fprintf(th, "#if defined(BCS) && defined(BITSTATE)\n");
+ fprintf(th, " #ifndef NO_CTX\n");
+ fprintf(th, " #define STORE_CTX 1\n");
+ fprintf(th, " #endif\n");
+ fprintf(th, "#endif\n");
+
+ fprintf(th, "#ifdef NP\n");
if (!has_np)
- fprintf(th, "#define HAS_NP 2\n");
- fprintf(th, "#define VERI %d\n", nrRdy);
- fprintf(th, "#define endclaim 3 /* none */\n");
+ fprintf(th, " #define HAS_NP 2\n");
+ fprintf(th, " #define VERI %d /* np_ */\n", nrRdy);
fprintf(th, "#endif\n");
if (claimproc)
- { claimnr = fproc(claimproc);
- /* NP overrides claimproc */
- fprintf(th, "#if !defined(NOCLAIM) && !defined NP\n");
- fprintf(th, "#define VERI %d\n", claimnr);
- fprintf(th, "#define endclaim endstate%d\n", claimnr);
+ { claimnr = fproc(claimproc); /* the default claim */
+ fprintf(th, "#ifndef NOCLAIM\n");
+ fprintf(th, " #define NCLAIMS %d\n", nclaims);
+ fprintf(th, " #ifndef NP\n");
+ fprintf(th, " #define VERI %d\n", claimnr);
+ fprintf(th, " #endif\n");
fprintf(th, "#endif\n");
}
if (eventmap)
{ eventmapnr = fproc(eventmap);
fprintf(th, "#define EVENT_TRACE %d\n", eventmapnr);
- fprintf(th, "#define endevent endstate%d\n", eventmapnr);
+ fprintf(th, "#define endevent _endstate%d\n", eventmapnr);
if (eventmap[2] == 'o') /* ":notrace:" */
fprintf(th, "#define NEGATED_TRACE 1\n");
}
- fprintf(th, "typedef struct S_F_MAP {\n");
- fprintf(th, " char *fnm; int from; int upto;\n");
+ fprintf(th, "\ntypedef struct S_F_MAP {\n");
+ fprintf(th, " char *fnm;\n\tint from;\n\tint upto;\n");
fprintf(th, "} S_F_MAP;\n");
- fprintf(tc, "/*** Generated by %s ***/\n", Version);
+ fprintf(tc, "/*** Generated by %s ***/\n", SpinVersion);
fprintf(tc, "/*** From source: %s ***/\n\n", oFname->name);
ntimes(tc, 0, 1, Pre0);
@@ -304,19 +461,36 @@ doless:
case 2: fprintf(tc, "#include \"pan_t.h\"\n"); break;
}
+ if (separate != 2)
+ { fprintf(tc, "char *TrailFile = PanSource; /* default */\n");
+ fprintf(tc, "char *trailfilename;\n");
+ }
+
+ fprintf(tc, "#ifdef LOOPSTATE\n");
+ fprintf(tc, "double cnt_loops;\n");
+ fprintf(tc, "#endif\n");
+
fprintf(tc, "State A_Root; /* seed-state for cycles */\n");
fprintf(tc, "State now; /* the full state-vector */\n");
+ fprintf(tc, "#if NQS > 0\n");
+ fprintf(tc, "short q_flds[NQS+1];\n");
+ fprintf(tc, "short q_max[NQS+1];\n");
+ fprintf(tc, "#endif\n");
+
plunk_c_fcts(tc); /* State can be used in fcts */
if (separate != 2)
- ntimes(tc, 0, 1, Preamble);
- else
- fprintf(tc, "extern int verbose; extern long depth;\n");
+ { ntimes(tc, 0, 1, Preamble);
+ ntimes(tc, 0, 1, Separate); /* things that moved out of pan.h */
+ } else
+ { fprintf(tc, "extern int verbose;\n");
+ fprintf(tc, "extern long depth, depthfound;\n");
+ }
fprintf(tc, "#ifndef NOBOUNDCHECK\n");
- fprintf(tc, "#define Index(x, y)\tBoundcheck(x, y, II, tt, t)\n");
+ fprintf(tc, " #define Index(x, y)\tBoundcheck(x, y, II, tt, t)\n");
fprintf(tc, "#else\n");
- fprintf(tc, "#define Index(x, y)\tx\n");
+ fprintf(tc, " #define Index(x, y)\tx\n");
fprintf(tc, "#endif\n");
c_preview(); /* sets hastrack */
@@ -335,7 +509,7 @@ doless:
fprintf(tt, "}\n\n");
fprintf(tt, "void\nputpeg(int n, int m)\n");
fprintf(tt, "{ printf(\"%%5d\ttrans %%4d \", m, n);\n");
- fprintf(tt, " printf(\"file %%s line %%3d\\n\",\n");
+ fprintf(tt, " printf(\"%%s:%%d\\n\",\n");
fprintf(tt, " T_SRC[n].fl, T_SRC[n].ln);\n");
fprintf(tt, "}\n");
if (!merger)
@@ -359,13 +533,18 @@ doless:
}
fprintf(tm, "#define rand pan_rand\n");
+ fprintf(tm, "#define pthread_equal(a,b) ((a)==(b))\n");
fprintf(tm, "#if defined(HAS_CODE) && defined(VERBOSE)\n");
- fprintf(tm, " printf(\"Pr: %%d Tr: %%d\\n\", II, t->forw);\n");
+ fprintf(tm, " #ifdef BFS_PAR\n");
+ fprintf(tm, " bfs_printf(\"Pr: %%d Tr: %%d\\n\", II, t->forw);\n");
+ fprintf(tm, " #else\n");
+ fprintf(tm, " cpu_printf(\"Pr: %%d Tr: %%d\\n\", II, t->forw);\n");
+ fprintf(tm, " #endif\n");
fprintf(tm, "#endif\n");
fprintf(tm, " switch (t->forw) {\n");
} else
{ fprintf(tt, "#ifndef PEG\n");
- fprintf(tt, "#define tr_2_src(m,f,l)\n");
+ fprintf(tt, " #define tr_2_src(m,f,l)\n");
fprintf(tt, "#endif\n");
fprintf(tt, "void\nset_claim(void)\n{\tTrans *T;\n");
fprintf(tt, "\textern Trans ***trans;\n");
@@ -373,8 +552,9 @@ doless:
fprintf(tt, " char *, int, int, int);\n\n");
fprintf(tm, "#define rand pan_rand\n");
+ fprintf(tm, "#define pthread_equal(a,b) ((a)==(b))\n");
fprintf(tm, "#if defined(HAS_CODE) && defined(VERBOSE)\n");
- fprintf(tm, " printf(\"Pr: %%d Tr: %%d\\n\", II, forw);\n");
+ fprintf(tm, " cpu_printf(\"Pr: %%d Tr: %%d\\n\", II, forw);\n");
fprintf(tm, "#endif\n");
fprintf(tm, " switch (forw) {\n");
}
@@ -404,24 +584,47 @@ doless:
fprintf(tb, " case 0: goto R999; /* nothing to undo */\n");
for (p = rdy; p; p = p->nxt)
- putproc(p);
-
+ { putproc(p);
+ }
if (separate != 2)
- { fprintf(th, "struct {\n");
- fprintf(th, " int tp; short *src;\n");
- fprintf(th, "} src_all[] = {\n");
+ { fprintf(th, "\n");
+ for (p = rdy; p; p = p->nxt)
+ fprintf(th, "extern short src_ln%d[];\n", p->tn);
+ for (p = rdy; p; p = p->nxt)
+ fprintf(th, "extern S_F_MAP src_file%d[];\n", p->tn);
+ fprintf(th, "\n");
+
+ fprintf(tc, "uchar reached%d[3]; /* np_ */\n", nrRdy);
+ fprintf(tc, "uchar *loopstate%d; /* np_ */\n", nrRdy);
+
+ fprintf(tc, "struct {\n");
+ fprintf(tc, " int tp; short *src;\n");
+ fprintf(tc, "} src_all[] = {\n");
for (p = rdy; p; p = p->nxt)
- fprintf(th, " { %d, &src_ln%d[0] },\n",
+ fprintf(tc, " { %d, &src_ln%d[0] },\n",
p->tn, p->tn);
- fprintf(th, " { 0, (short *) 0 }\n");
- fprintf(th, "};\n");
- fprintf(th, "short *frm_st0;\n"); /* records src states for transitions in never claim */
+ fprintf(tc, " { 0, (short *) 0 }\n");
+ fprintf(tc, "};\n");
+
+ fprintf(tc, "S_F_MAP *flref[] = {\n"); /* 5.3.0 */
+ for (p = rdy; p; p = p->nxt)
+ { fprintf(tc, " src_file%d%c\n", p->tn, p->nxt?',':' ');
+ }
+ fprintf(tc, "};\n\n");
} else
- { fprintf(th, "extern short *frm_st0;\n");
+ { fprintf(tc, "extern uchar reached%d[3]; /* np_ */\n", nrRdy);
}
- gencodetable(th);
+ gencodetable(tc); /* was th */
+
+ if (Unique < (1 << (8*sizeof(unsigned char)) )) /* was uniq before */
+ { fprintf(th, "#define T_ID unsigned char\n");
+ } else if (Unique < (1 << (8*sizeof(unsigned short)) ))
+ { fprintf(th, "#define T_ID unsigned short\n");
+ } else
+ { fprintf(th, "#define T_ID unsigned int\n");
+ }
if (separate != 1)
{ tm_predef_np();
@@ -438,13 +641,13 @@ doless:
genheader();
if (separate == 1)
{ fprintf(th, "#define FORWARD_MOVES\t\"pan_s.m\"\n");
- fprintf(th, "#define REVERSE_MOVES\t\"pan_s.b\"\n");
+ fprintf(th, "#define BACKWARD_MOVES\t\"pan_s.b\"\n");
fprintf(th, "#define SEPARATE\n");
fprintf(th, "#define TRANSITIONS\t\"pan_s.t\"\n");
fprintf(th, "extern void ini_claim(int, int);\n");
} else
{ fprintf(th, "#define FORWARD_MOVES\t\"pan.m\"\n");
- fprintf(th, "#define REVERSE_MOVES\t\"pan.b\"\n");
+ fprintf(th, "#define BACKWARD_MOVES\t\"pan.b\"\n");
fprintf(th, "#define TRANSITIONS\t\"pan.t\"\n");
}
genaddproc();
@@ -456,33 +659,37 @@ doless:
if (!run) fatal("no runable process", (char *)0);
fprintf(tc, "void\n");
fprintf(tc, "active_procs(void)\n{\n");
+
+ fprintf(tc, " if (reversing == 0) {\n");
reverse_procs(run);
+ fprintf(tc, " } else {\n");
+ forward_procs(run);
+ fprintf(tc, " }\n");
+
fprintf(tc, "}\n");
ntimes(tc, 0, 1, Dfa);
ntimes(tc, 0, 1, Xpt);
fprintf(th, "#define NTRANS %d\n", uniq);
- fprintf(th, "#ifdef PEG\n");
- fprintf(th, "long peg[NTRANS];\n");
- fprintf(th, "#endif\n");
-
if (u_sync && !u_async)
- spit_recvs(th, tc);
+ { spit_recvs(th, tc);
+ }
} else
{ genheader();
fprintf(th, "#define FORWARD_MOVES\t\"pan_t.m\"\n");
- fprintf(th, "#define REVERSE_MOVES\t\"pan_t.b\"\n");
+ fprintf(th, "#define BACKWARD_MOVES\t\"pan_t.b\"\n");
fprintf(th, "#define TRANSITIONS\t\"pan_t.t\"\n");
fprintf(tc, "extern int Maxbody;\n");
fprintf(tc, "#if VECTORSZ>32000\n");
- fprintf(tc, "extern int proc_offset[];\n");
+ fprintf(tc, " extern int *proc_offset;\n");
fprintf(tc, "#else\n");
- fprintf(tc, "extern short proc_offset[];\n");
+ fprintf(tc, " extern short *proc_offset;\n");
fprintf(tc, "#endif\n");
- fprintf(tc, "extern uchar proc_skip[];\n");
+ fprintf(tc, "extern uchar *proc_skip;\n");
fprintf(tc, "extern uchar *reached[];\n");
fprintf(tc, "extern uchar *accpstate[];\n");
fprintf(tc, "extern uchar *progstate[];\n");
+ fprintf(tc, "extern uchar *loopstate[];\n");
fprintf(tc, "extern uchar *stopstate[];\n");
fprintf(tc, "extern uchar *visstate[];\n\n");
fprintf(tc, "extern short *mapstate[];\n");
@@ -491,7 +698,7 @@ doless:
fprintf(tc, "\textern State now;\n");
fprintf(tc, "\textern void set_claim(void);\n\n");
fprintf(tc, "#ifdef PROV\n");
- fprintf(tc, "#include PROV\n");
+ fprintf(tc, " #include PROV\n");
fprintf(tc, "#endif\n");
fprintf(tc, "\tset_claim();\n");
genother();
@@ -509,13 +716,42 @@ doless:
fprintf(tc, "int\nrev_claim(int backw)\n{ return 0; }\n");
fprintf(tc, "#include TRANSITIONS\n");
}
- if (separate != 1)
- ntimes(tc, 0, 1, Nvr1);
if (separate != 2)
{ c_wrapper(tc);
c_chandump(tc);
}
+
+ fprintf(th, "#if defined(BFS_PAR) || NCORE>1\n");
+ fprintf(th, " void e_critical(int);\n");
+ fprintf(th, " void x_critical(int);\n");
+ fprintf(th, " #ifdef BFS_PAR\n");
+ fprintf(th, " void bfs_main(int, int);\n");
+ fprintf(th, " void bfs_report_mem(void);\n");
+ fprintf(th, " #endif\n");
+ fprintf(th, "#endif\n");
+
+ fprintf(th, "\n\n/* end of PAN_H */\n#endif\n");
+ fclose(th);
+ fclose(tt);
+ fclose(tm);
+ fclose(tb);
+
+ if (!(th = fopen("pan.p", MFLAGS)))
+ { printf("spin: cannot create pan.p for -DBFS_PAR\n");
+ return; /* we're done anyway */
+ }
+
+ ntimes(th, 0, 1, pan_par); /* BFS_PAR */
+ fclose(th);
+
+ fprintf(tc, "\nTrans *t_id_lkup[%d];\n\n", globmax+1);
+
+ if (separate != 2)
+ { fprintf(tc, "\n#ifdef BFS_PAR\n\t#include \"pan.p\"\n#endif\n");
+ }
+ fprintf(tc, "\n/* end of pan.c */\n");
+ fclose(tc);
}
static int
@@ -537,13 +773,13 @@ dolen(Symbol *s, char *pre, int pid, int ai, int qln)
fprintf(tc, "%s(", pre);
if (!(s->hidden&1))
{ if (s->context)
- fprintf(tc, "((P%d *)this)->", pid);
+ fprintf(tc, "(int) ( ((P%d *)this)->", pid);
else
- fprintf(tc, "now.");
+ fprintf(tc, "(int) ( now.");
}
fprintf(tc, "%s", s->name);
- if (qln > 1) fprintf(tc, "[%d]", ai);
- fprintf(tc, ")");
+ if (qln > 1 || s->isarray) fprintf(tc, "[%d]", ai);
+ fprintf(tc, ") )");
}
struct AA { char TT[9]; char CC[8]; };
@@ -712,47 +948,60 @@ genconditionals(void)
fprintf(tc, "}\n");
}
+extern int find_min(Sequence *);
+extern int find_max(Sequence *);
+
static void
putproc(ProcList *p)
{ Pid = p->tn;
Det = p->det;
- if (Pid == claimnr
+ if (pid_is_claim(Pid)
&& separate == 1)
{ fprintf(th, "extern uchar reached%d[];\n", Pid);
#if 0
- fprintf(th, "extern short nstates%d;\n", Pid);
+ fprintf(th, "extern short _nstates%d;\n", Pid);
#else
- fprintf(th, "\n#define nstates%d %d\t/* %s */\n",
+ fprintf(th, "\n#define _nstates%d %d\t/* %s */\n",
Pid, p->s->maxel, p->n->name);
#endif
fprintf(th, "extern short src_ln%d[];\n", Pid);
+ fprintf(th, "extern uchar *loopstate%d;\n", Pid);
fprintf(th, "extern S_F_MAP src_file%d[];\n", Pid);
- fprintf(th, "#define endstate%d %d\n",
+ fprintf(th, "#define _endstate%d %d\n",
Pid, p->s->last?p->s->last->seqno:0);
- fprintf(th, "#define src_claim src_ln%d\n", claimnr);
-
return;
}
- if (Pid != claimnr
+ if (!pid_is_claim(Pid)
&& separate == 2)
{ fprintf(th, "extern short src_ln%d[];\n", Pid);
+ fprintf(th, "extern uchar *loopstate%d;\n", Pid);
return;
}
AllGlobal = (p->prov)?1:0; /* process has provided clause */
- fprintf(th, "\n#define nstates%d %d\t/* %s */\n",
+ fprintf(th, "\n#define _nstates%d %d\t/* %s */\n",
Pid, p->s->maxel, p->n->name);
- if (Pid == claimnr)
- fprintf(th, "#define nstates_claim nstates%d\n", Pid);
+/* new */
+ fprintf(th, "#define minseq%d %d\n", Pid, find_min(p->s));
+ fprintf(th, "#define maxseq%d %d\n", Pid, find_max(p->s));
+
+/* end */
+
if (Pid == eventmapnr)
- fprintf(th, "#define nstates_event nstates%d\n", Pid);
+ fprintf(th, "#define nstates_event _nstates%d\n", Pid);
+
+ fprintf(th, "#define _endstate%d %d\n", Pid, p->s->last?p->s->last->seqno:0);
- fprintf(th, "#define endstate%d %d\n",
- Pid, p->s->last->seqno);
- fprintf(tm, "\n /* PROC %s */\n", p->n->name);
- fprintf(tb, "\n /* PROC %s */\n", p->n->name);
+ if (p->b == N_CLAIM || p->b == E_TRACE || p->b == N_TRACE)
+ { fprintf(tm, "\n /* CLAIM %s */\n", p->n->name);
+ fprintf(tb, "\n /* CLAIM %s */\n", p->n->name);
+ }
+ else
+ { fprintf(tm, "\n /* PROC %s */\n", p->n->name);
+ fprintf(tb, "\n /* PROC %s */\n", p->n->name);
+ }
fprintf(tt, "\n /* proctype %d: %s */\n", Pid, p->n->name);
fprintf(tt, "\n trans[%d] = (Trans **)", Pid);
fprintf(tt, " emalloc(%d*sizeof(Trans *));\n\n", p->s->maxel);
@@ -761,7 +1010,6 @@ putproc(ProcList *p)
{ fprintf(th, "\n#define in_s_scope(x_y3_) 0");
fprintf(tc, "\n#define in_r_scope(x_y3_) 0");
}
-
put_seq(p->s, 2, 0);
if (Pid == eventmapnr)
{ fprintf(th, "\n\n");
@@ -947,10 +1195,10 @@ put_sub(Element *e, int Tt0, int Tt1)
if (e->n->ntyp == D_STEP)
{ int inherit = (e->status&(ATOM|L_ATOM));
fprintf(tm, "\tcase %d: ", uniq++);
- fprintf(tm, "/* STATE %d - line %d %s - [",
- e->seqno, e->n->ln, e->n->fn->name);
+ fprintf(tm, "// STATE %d - %s:%d - [",
+ e->seqno, e->n->fn->name, e->n->ln);
comment(tm, e->n, 0);
- fprintf(tm, "] */\n\t\t");
+ fprintf(tm, "]\n\t\t");
if (s->last->n->ntyp == BREAK)
OkBreak = target(huntele(s->last->nxt,
@@ -971,7 +1219,7 @@ put_sub(Element *e, int Tt0, int Tt1)
}
fprintf(tb, "\tcase %d: ", uniq-1);
- fprintf(tb, "/* STATE %d */\n", e->seqno);
+ fprintf(tb, "// STATE %d\n", e->seqno);
fprintf(tb, "\t\tsv_restor();\n");
fprintf(tb, "\t\tgoto R999;\n");
if (e->nxt)
@@ -1024,7 +1272,7 @@ typedef struct CaseCache {
struct CaseCache *nxt;
} CaseCache;
-CaseCache *casing[6];
+static CaseCache *casing[6];
static int
identical(Lextok *p, Lextok *q)
@@ -1076,6 +1324,9 @@ advance(Element *e, int stopat)
if (stopat)
while (f && f->seqno != stopat)
{ f = findnext(f);
+ if (!f)
+ { break;
+ }
switch (f->n->ntyp) {
case GOTO:
case '.':
@@ -1084,8 +1335,7 @@ advance(Element *e, int stopat)
break;
default:
return f;
- }
- }
+ } }
return (Element *) 0;
}
@@ -1107,18 +1357,16 @@ equiv_merges(Element *a, Element *b)
if (!stopat_a && !stopat_b)
return 1;
- for (;;)
- {
- f = advance(a, stopat_a);
- g = advance(b, stopat_b);
- if (!f && !g)
- return 1;
- if (f && g)
- return identical(f->n, g->n);
- else
- return 0;
- }
- return 1;
+ f = advance(a, stopat_a);
+ g = advance(b, stopat_b);
+
+ if (!f && !g)
+ return 1;
+
+ if (f && g)
+ return identical(f->n, g->n);
+
+ return 0;
}
static CaseCache *
@@ -1174,6 +1422,7 @@ nr_bup(Element *e)
switch (e->n->ntyp) {
case ASGN:
+ if (check_track(e->n) == STRUCT) { break; }
nr++;
break;
case 'r':
@@ -1234,10 +1483,10 @@ nrhops(Element *e)
}
if (f && !f->merge && !f->merge_single && f->seqno != stopat)
- { fprintf(tm, "\n\t\tbad hop %s:%d -- at %d, <",
+ { fprintf(tm, "\n\t\t// bad hop %s:%d -- at %d, <",
f->n->fn->name,f->n->ln, f->seqno);
comment(tm, f->n, 0);
- fprintf(tm, "> looking for %d -- merge %d:%d:%d\n\t\t",
+ fprintf(tm, "> looking for %d -- merge %d:%d:%d ",
stopat, f->merge, f->merge_start, f->merge_single);
break;
}
@@ -1258,18 +1507,20 @@ check_needed(void)
}
static void
-doforward(FILE *tm, Element *e)
+doforward(FILE *tm_fd, Element *e)
{ FSM_use *u;
- putstmnt(tm, e->n, e->seqno);
+ putstmnt(tm_fd, e->n, e->seqno);
if (e->n->ntyp != ELSE && Det)
- { fprintf(tm, ";\n\t\tif (trpt->o_pm&1)\n\t\t");
- fprintf(tm, "\tuerror(\"non-determinism in D_proctype\")");
+ { fprintf(tm_fd, ";\n\t\tif (trpt->o_pm&1)\n\t\t");
+ fprintf(tm_fd, "\tuerror(\"non-determinism in D_proctype\")");
}
if (deadvar && !has_code)
for (u = e->dead; u; u = u->nxt)
- { fprintf(tm, ";\n\t\t/* dead %d: %s */ ",
+ { fprintf(tm_fd, ";\n\t\t");
+ fprintf(tm_fd, "if (TstOnly) return 1; /* TT */\n");
+ fprintf(tm_fd, "\t\t/* dead %d: %s */ ",
u->special, u->var->name);
switch (u->special) {
@@ -1281,10 +1532,10 @@ doforward(FILE *tm, Element *e)
}
if (e->n->ntyp != 'r')
{ XZ.sym = u->var;
- fprintf(tm, "\n#ifdef HAS_CODE\n");
- fprintf(tm, "\t\tif (!readtrail)\n");
- fprintf(tm, "#endif\n\t\t\t");
- putname(tm, "", &XZ, 0, " = 0");
+ fprintf(tm_fd, "\n#ifdef HAS_CODE\n");
+ fprintf(tm_fd, "\t\tif (!readtrail)\n");
+ fprintf(tm_fd, "#endif\n\t\t\t");
+ putname(tm_fd, "", &XZ, 0, " = 0");
break;
} /* else fall through */
case 1: /* dead after read -- add asgn of rval -- needs bup */
@@ -1292,20 +1543,20 @@ doforward(FILE *tm, Element *e)
CnT[YZcnt]++; /* this step added bups */
if (multi_oval)
{ check_needed();
- fprintf(tm, "(trpt+1)->bup.ovals[%d] = ",
+ fprintf(tm_fd, "(trpt+1)->bup.ovals[%d] = ",
multi_oval-1);
multi_oval++;
} else
- fprintf(tm, "(trpt+1)->bup.oval = ");
- putname(tm, "", &YZ[YZmax], 0, ";\n");
- fprintf(tm, "#ifdef HAS_CODE\n");
- fprintf(tm, "\t\tif (!readtrail)\n");
- fprintf(tm, "#endif\n\t\t\t");
- putname(tm, "", &YZ[YZmax], 0, " = 0");
+ fprintf(tm_fd, "(trpt+1)->bup.oval = ");
+ putname(tm_fd, "", &YZ[YZmax], 0, ";\n");
+ fprintf(tm_fd, "#ifdef HAS_CODE\n");
+ fprintf(tm_fd, "\t\tif (!readtrail)\n");
+ fprintf(tm_fd, "#endif\n\t\t\t");
+ putname(tm_fd, "", &YZ[YZmax], 0, " = 0");
YZmax++;
break;
} }
- fprintf(tm, ";\n\t\t");
+ fprintf(tm_fd, ";\n\t\t");
}
static int
@@ -1318,7 +1569,7 @@ dobackward(Element *e, int casenr)
if (!didcase)
{ fprintf(tb, "\n\tcase %d: ", casenr);
- fprintf(tb, "/* STATE %d */\n\t\t", e->seqno);
+ fprintf(tb, "// STATE %d\n\t\t", e->seqno);
didcase++;
}
@@ -1412,7 +1663,7 @@ case_cache(Element *e, int a)
{ int bupcase = 0, casenr = uniq, fromcache = 0;
CaseCache *Cached = (CaseCache *) 0;
Element *f, *g;
- int j, nrbups, mark, target;
+ int j, nrbups, mark, ntarget;
extern int ccache;
mark = (e->status&ATOM); /* could lose atomicity in a merge chain */
@@ -1439,17 +1690,17 @@ case_cache(Element *e, int a)
fprintf(tt, "\ttrans[%d][%d]\t= ", Pid, e->seqno);
if (ccache
- && Pid != claimnr
+ && !pid_is_claim(Pid)
&& Pid != eventmapnr
&& (Cached = prev_case(e, Pid)))
{ bupcase = Cached->b;
casenr = Cached->m;
fromcache = 1;
- fprintf(tm, "/* STATE %d - line %d %s - [",
- e->seqno, e->n->ln, e->n->fn->name);
+ fprintf(tm, "// STATE %d - %s:%d - [",
+ e->seqno, e->n->fn->name, e->n->ln);
comment(tm, e->n, 0);
- fprintf(tm, "] (%d:%d - %d) same as %d (%d:%d - %d) */\n",
+ fprintf(tm, "] (%d:%d - %d) same as %d (%d:%d - %d)\n",
e->merge_start, e->merge, e->merge_in,
casenr,
Cached->e->merge_start, Cached->e->merge, Cached->e->merge_in);
@@ -1457,17 +1708,17 @@ case_cache(Element *e, int a)
goto gotit;
}
- fprintf(tm, "\tcase %d: /* STATE %d - line %d %s - [",
- uniq++, e->seqno, e->n->ln, e->n->fn->name);
+ fprintf(tm, "\tcase %d: // STATE %d - %s:%d - [",
+ uniq++, e->seqno, e->n->fn->name, e->n->ln);
comment(tm, e->n, 0);
nrbups = (e->merge || e->merge_start) ? nrhops(e) : nr_bup(e);
- fprintf(tm, "] (%d:%d:%d - %d) */\n\t\t",
+ fprintf(tm, "] (%d:%d:%d - %d)\n\t\t",
e->merge_start, e->merge, nrbups, e->merge_in);
if (nrbups > MAXMERGE-1)
fatal("merge requires more than 256 bups", (char *)0);
- if (e->n->ntyp != 'r' && Pid != claimnr && Pid != eventmapnr)
+ if (e->n->ntyp != 'r' && !pid_is_claim(Pid) && Pid != eventmapnr)
fprintf(tm, "IfNotBlocked\n\t\t");
if (multi_needed != 0 || multi_undo != 0)
@@ -1482,18 +1733,29 @@ case_cache(Element *e, int a)
memset(CnT, 0, sizeof(CnT));
YZmax = YZcnt = 0;
-/* NEW 4.2.6 */
- if (Pid == claimnr)
- {
- fprintf(tm, "\n#if defined(VERI) && !defined(NP)\n\t\t");
- fprintf(tm, "{ static int reported%d = 0;\n\t\t", e->seqno);
- /* source state changes in retrans and must be looked up in frm_st0[t->forw] */
- fprintf(tm, " if (verbose && !reported%d)\n\t\t", e->seqno);
- fprintf(tm, " { printf(\"depth %%d: Claim reached state %%d (line %%d)\\n\",\n\t\t");
- fprintf(tm, " depth, frm_st0[t->forw], src_claim[%d]);\n\t\t", e->seqno);
- fprintf(tm, " reported%d = 1;\n\t\t", e->seqno);
- fprintf(tm, " fflush(stdout);\n\t\t");
- fprintf(tm, "} }\n");
+/* new 4.2.6, revised 6.0.0 */
+ if (pid_is_claim(Pid))
+ { fprintf(tm, "\n#if defined(VERI) && !defined(NP)\n");
+ fprintf(tm, "#if NCLAIMS>1\n\t\t");
+ fprintf(tm, "{ static int reported%d = 0;\n\t\t", e->seqno);
+ fprintf(tm, " if (verbose && !reported%d)\n\t\t", e->seqno);
+ fprintf(tm, " { int nn = (int) ((Pclaim *)pptr(0))->_n;\n\t\t");
+ fprintf(tm, " printf(\"depth %%ld: Claim %%s (%%d), state %%d (line %%d)\\n\",\n\t\t");
+ fprintf(tm, " depth, procname[spin_c_typ[nn]], nn, ");
+ fprintf(tm, "(int) ((Pclaim *)pptr(0))->_p, src_claim[ (int) ((Pclaim *)pptr(0))->_p ]);\n\t\t");
+ fprintf(tm, " reported%d = 1;\n\t\t", e->seqno);
+ fprintf(tm, " fflush(stdout);\n\t\t");
+ fprintf(tm, "} }\n");
+ fprintf(tm, "#else\n\t\t");
+ fprintf(tm, "{ static int reported%d = 0;\n\t\t", e->seqno);
+ fprintf(tm, " if (verbose && !reported%d)\n\t\t", e->seqno);
+ fprintf(tm, " { printf(\"depth %%d: Claim, state %%d (line %%d)\\n\",\n\t\t");
+ fprintf(tm, " (int) depth, (int) ((Pclaim *)pptr(0))->_p, ");
+ fprintf(tm, "src_claim[ (int) ((Pclaim *)pptr(0))->_p ]);\n\t\t");
+ fprintf(tm, " reported%d = 1;\n\t\t", e->seqno);
+ fprintf(tm, " fflush(stdout);\n\t\t");
+ fprintf(tm, "} }\n");
+ fprintf(tm, "#endif\n");
fprintf(tm, "#endif\n\t\t");
}
/* end */
@@ -1504,32 +1766,32 @@ case_cache(Element *e, int a)
doforward(tm, e);
if (e->merge_start)
- target = e->merge_start;
+ ntarget = e->merge_start;
else
- target = e->merge;
+ ntarget = e->merge;
- if (target)
+ if (ntarget)
{ f = e;
more: if (f->n->ntyp == GOTO)
{ g = get_lab(f->n, 1);
- if (g->seqno == target)
+ if (g->seqno == ntarget)
f = g;
else
- f = huntele(g, f->status, target);
+ f = huntele(g, f->status, ntarget);
} else
f = f->nxt;
- if (f && f->seqno != target)
+ if (f && f->seqno != ntarget)
{ if (!f->merge && !f->merge_single)
{ fprintf(tm, "/* stop at bad hop %d, %d */\n\t\t",
- f->seqno, target);
+ f->seqno, ntarget);
goto out;
}
fprintf(tm, "/* merge: ");
comment(tm, f->n, 0);
- fprintf(tm, "(%d, %d, %d) */\n\t\t", f->merge, f->seqno, target);
+ fprintf(tm, "(%d, %d, %d) */\n\t\t", f->merge, f->seqno, ntarget);
fprintf(tm, "reached[%d][%d] = 1;\n\t\t", Pid, f->seqno);
YZcnt++;
lab_transfer(e, f);
@@ -1547,8 +1809,8 @@ out:
multi_needed = 0;
didcase = 0;
- if (target)
- lastfirst(target, e, casenr); /* mergesteps only */
+ if (ntarget)
+ lastfirst(ntarget, e, casenr); /* mergesteps only */
dobackward(e, casenr); /* the original step */
@@ -1557,7 +1819,7 @@ out:
if (e->merge || e->merge_start)
{ if (!didcase)
{ fprintf(tb, "\n\tcase %d: ", casenr);
- fprintf(tb, "/* STATE %d */", e->seqno);
+ fprintf(tb, "// STATE %d", e->seqno);
didcase++;
} else
fprintf(tb, ";");
@@ -1607,8 +1869,8 @@ put_el(Element *e, int Tt0, int Tt1)
} else
a = 0;
if (g
- && (g->status&CHECK2 /* entering remotely ref'd state */
- || e->status&CHECK2)) /* leaving remotely ref'd state */
+ && ((g->status&CHECK2) /* entering remotely ref'd state */
+ || (e->status&CHECK2))) /* leaving remotely ref'd state */
e->status |= I_GLOB;
/* don't remove dead edges in here, to preserve structure of fsm */
@@ -1758,8 +2020,8 @@ put_seq(Sequence *s, int Tt0, int Tt1)
{ fprintf(tt, "#if 0\n\t/* dead link: */\n");
deadlink = 1;
if (verbose&32)
- printf("spin: line %3d %s, Warning: condition is always false\n",
- g->n->ln, g->n->fn?g->n->fn->name:"");
+ printf("spin: %s:%d, warning, condition is always false\n",
+ g->n->fn?g->n->fn->name:"", g->n->ln);
} else
deadlink = 0;
if (0) printf(" settr %d %d\n", a, 0);
@@ -1867,7 +2129,7 @@ find_target(Element *e)
case BREAK:
if (e->nxt)
{ f = find_target(huntele(e->nxt, e->status, -1));
- break; /* 4.3.0 -- was missing */
+ break; /* new 5.0 -- was missing */
}
/* else fall through */
default:
@@ -1888,6 +2150,26 @@ target(Element *e)
}
static int
+seq_has_el(Sequence *s, Element *g) /* new to version 5.0 */
+{ Element *f;
+ SeqList *h;
+
+ for (f = s->frst; f; f = f->nxt) /* g in same atomic? */
+ { if (f == g)
+ { return 1;
+ }
+ if (f->status & CHECK3)
+ { continue;
+ }
+ f->status |= CHECK3; /* protect against cycles */
+ for (h = f->sub; h; h = h->nxt)
+ { if (h->this && seq_has_el(h->this, g))
+ { return 1;
+ } } }
+ return 0;
+}
+
+static int
scan_seq(Sequence *s)
{ Element *f, *g;
SeqList *h;
@@ -1896,20 +2178,22 @@ scan_seq(Sequence *s)
{ if ((f->status&CHECK2)
|| has_global(f->n))
return 1;
- if (f->n->ntyp == GOTO) /* may reach other atomic */
- {
-#if 0
- /* if jumping from an atomic without globals into
- * one with globals, this does the wrong thing
+ if (f->n->ntyp == GOTO /* may exit or reach other atomic */
+ && !(f->status & D_ATOM)) /* cannot jump from d_step */
+ { /* consider jump from an atomic without globals into
+ * an atomic with globals
* example by Claus Traulsen, 22 June 2007
*/
g = target(f);
+#if 1
+ if (g && !seq_has_el(s, g)) /* not internal to this atomic/dstep */
+
+#else
if (g
&& !(f->status & L_ATOM)
&& !(g->status & (ATOM|L_ATOM)))
#endif
- { fprintf(tt, " /* mark-down line %d */\n",
- f->n->ln);
+ { fprintf(tt, "\t/* mark-down line %d status %d = %d */\n", f->n->ln, f->status, (f->status & D_ATOM));
return 1; /* assume worst case */
} }
for (h = f->sub; h; h = h->nxt)
@@ -1937,9 +2221,26 @@ glob_args(Lextok *n)
return result;
}
+static int
+proc_is_safe(const Lextok *n)
+{ ProcList *p;
+ /* not safe unless no local var inits are used */
+ /* note that a local variable init could refer to a global */
+
+ for (p = rdy; p; p = p->nxt)
+ { if (strcmp(n->sym->name, p->n->name) == 0)
+ { /* printf("proc %s safety: %d\n", p->n->name, p->unsafe); */
+ return (p->unsafe != 0);
+ } }
+/* non_fatal("bad call to proc_is_safe", (char *) 0); */
+ /* cannot happen */
+ return 0;
+}
+
int
has_global(Lextok *n)
-{ Lextok *v; extern int runsafe;
+{ Lextok *v;
+ static Symbol *n_seen = (Symbol *) 0;
if (!n) return 0;
if (AllGlobal) return 1; /* global provided clause */
@@ -1968,6 +2269,14 @@ has_global(Lextok *n)
case LEN: return (((n->sym->xu)&(XR|XS|XX)) != (XR|XS));
case NAME:
+ if (strcmp(n->sym->name, "_priority") == 0)
+ { if (old_priority_rules)
+ { if (n_seen != n->sym)
+ fatal("cannot refer to _priority with -o6", (char *) 0);
+ n_seen = n->sym;
+ }
+ return 0;
+ }
if (n->sym->context
|| (n->sym->hidden&64)
|| strcmp(n->sym->name, "_pid") == 0
@@ -1975,14 +2284,15 @@ has_global(Lextok *n)
return 0;
return 1;
- case RUN: return 1-runsafe;
+ case RUN:
+ return proc_is_safe(n);
case C_CODE: case C_EXPR:
return glob_inline(n->sym->name);
case ENABLED: case PC_VAL: case NONPROGRESS:
- case 'p': case 'q':
- case TIMEOUT:
+ case 'p': case 'q':
+ case TIMEOUT: case SET_P: case GET_P:
return 1;
/* @ was 1 (global) since 2.8.5
@@ -2017,11 +2327,12 @@ static void
Bailout(FILE *fd, char *str)
{
if (!GenCode)
- fprintf(fd, "continue%s", str);
- else if (IsGuard)
- fprintf(fd, "%s%s", NextLab[Level], str);
- else
- fprintf(fd, "Uerror(\"block in step seq\")%s", str);
+ { fprintf(fd, "continue%s", str);
+ } else if (IsGuard)
+ { fprintf(fd, "%s%s", NextLab[Level], str);
+ } else
+ { fprintf(fd, "Uerror(\"block in d_step seq\")%s", str);
+ }
}
#define cat0(x) putstmnt(fd,now->lft,m); fprintf(fd, x); \
@@ -2029,6 +2340,7 @@ Bailout(FILE *fd, char *str)
#define cat1(x) fprintf(fd,"("); cat0(x); fprintf(fd,")")
#define cat2(x,y) fprintf(fd,x); putstmnt(fd,y,m)
#define cat3(x,y,z) fprintf(fd,x); putstmnt(fd,y,m); fprintf(fd,z)
+#define cat30(x,y,z) fprintf(fd,x,0); putstmnt(fd,y,m); fprintf(fd,z)
void
putstmnt(FILE *fd, Lextok *now, int m)
@@ -2070,12 +2382,14 @@ putstmnt(FILE *fd, Lextok *now, int m)
else
fprintf(fd, "((trpt->tau)&1)");
if (GenCode)
- printf("spin: line %3d, warning: 'timeout' in d_step sequence\n",
- lineno);
+ printf("spin: %s:%d, warning, 'timeout' in d_step sequence\n",
+ Fname->name, lineno);
/* is okay as a guard */
break;
case RUN:
+ if (now->sym == NULL)
+ fatal("internal error pangen2.c", (char *) 0);
if (claimproc
&& strcmp(now->sym->name, claimproc) == 0)
fatal("claim %s, (not runnable)", claimproc);
@@ -2084,29 +2398,57 @@ putstmnt(FILE *fd, Lextok *now, int m)
fatal("eventmap %s, (not runnable)", eventmap);
if (GenCode)
- fatal("'run' in d_step sequence (use atomic)",
- (char *)0);
+ fatal("'run' in d_step sequence (use atomic)", (char *)0);
- fprintf(fd,"addproc(%d", fproc(now->sym->name));
+ fprintf(fd,"addproc(II, %d, %d",
+ (now->val > 0 && !old_priority_rules) ? now->val : 1,
+ fproc(now->sym->name));
for (v = now->lft, i = 0; v; v = v->rgt, i++)
{ cat2(", ", v->lft);
}
check_param_count(i, now);
if (i > Npars)
- { printf("\t%d parameters used, max %d expected\n", i, Npars);
- fatal("too many parameters in run %s(...)",
- now->sym->name);
+ { /* printf("\t%d parameters used, max %d expected\n", i, Npars); */
+ fatal("too many parameters in run %s(...)", now->sym->name);
}
for ( ; i < Npars; i++)
fprintf(fd, ", 0");
fprintf(fd, ")");
+#if 0
+ /* process now->sym->name has run priority now->val */
+ if (now->val > 0 && now->val < 256 && !old_priority_rules)
+ { fprintf(fd, " && (((P0 *)pptr(now._nr_pr - 1))->_priority = %d)", now->val);
+ }
+#endif
+ if (now->val < 0 || now->val > 255) /* 0 itself is allowed */
+ { fatal("bad process in run %s, valid range: 1..255", now->sym->name);
+ }
break;
case ENABLED:
cat3("enabled(II, ", now->lft, ")");
break;
+ case GET_P:
+ if (old_priority_rules)
+ { fprintf(fd, "1");
+ } else
+ { cat3("get_priority(", now->lft, ")");
+ }
+ break;
+
+ case SET_P:
+ if (!old_priority_rules)
+ { fprintf(fd, "if (TstOnly) return 1; /* T30 */\n\t\t");
+ fprintf(fd, "set_priority(");
+ putstmnt(fd, now->lft->lft, m);
+ fprintf(fd, ", ");
+ putstmnt(fd, now->lft->rgt, m);
+ fprintf(fd, ")");
+ }
+ break;
+
case NONPROGRESS:
/* o_pm&4=progress, tau&128=claim stutter */
if (separate == 2)
@@ -2180,7 +2522,7 @@ putstmnt(FILE *fd, Lextok *now, int m)
case 's':
if (Pid == eventmapnr)
- { fprintf(fd, "if ((ot == EVENT_TRACE && _tp != 's') ");
+ { fprintf(fd, "if ((II == -EVENT_TRACE && _tp != 's') ");
putname(fd, "|| _qid+1 != ", now->lft, m, "");
for (v = now->rgt, i=0; v; v = v->rgt, i++)
{ if (v->lft->ntyp != CONST
@@ -2208,31 +2550,37 @@ putstmnt(FILE *fd, Lextok *now, int m)
break;
}
if (has_xu)
- { fprintf(fd, "\n#ifndef XUSAFE\n\t\t");
- putname(fd, "if (q_claim[", now->lft, m, "]&2) ");
- putname(fd, "q_S_check(", now->lft, m, ", II);");
- fprintf(fd, "\n#endif\n\t\t");
+ { fprintf(fd, "\n#if !defined(XUSAFE) && !defined(NOREDUCE)\n\t\t");
+ putname(fd, "if (q_claim[", now->lft, m, "]&2)\n\t\t");
+ putname(fd, "{ q_S_check(", now->lft, m, ", II);\n\t\t");
+ fprintf(fd, "}\n");
+ if (has_sorted && now->val == 1)
+ { putname(fd, "\t\tif (q_claim[", now->lft, m, "]&1)\n\t\t"); /* &1 iso &2 */
+ fprintf(fd, "{ uerror(\"sorted send on xr channel violates po reduction\");\n\t\t");
+ fprintf(fd, "}\n");
+ }
+ fprintf(fd, "#endif\n\t\t");
}
fprintf(fd, "if (q_%s",
(u_sync > 0 && u_async == 0)?"len":"full");
putname(fd, "(", now->lft, m, "))\n");
if (m_loss)
- fprintf(fd, "\t\t{ nlost++; delta_m = 1; } else {");
- else
+ { fprintf(fd, "\t\t{ nlost++; delta_m = 1; } else {");
+ } else
{ fprintf(fd, "\t\t\t");
Bailout(fd, ";");
}
- if (has_enabled)
- fprintf(fd, "\n\t\tif (TstOnly) return 1;");
+ if (has_enabled || has_priority)
+ fprintf(fd, "\n\t\tif (TstOnly) return 1; /* T1 */");
if (u_sync && !u_async && rvopt)
fprintf(fd, "\n\n\t\tif (no_recvs(II)) continue;\n");
fprintf(fd, "\n#ifdef HAS_CODE\n");
fprintf(fd, "\t\tif (readtrail && gui) {\n");
- fprintf(fd, "\t\t\tchar simtmp[32];\n");
+ fprintf(fd, "\t\t\tchar simtmp[64];\n");
putname(fd, "\t\t\tsprintf(simvals, \"%%d!\", ", now->lft, m, ");\n");
_isok++;
for (v = now->rgt, i = 0; v; v = v->rgt, i++)
@@ -2256,9 +2604,9 @@ putstmnt(FILE *fd, Lextok *now, int m)
printf(" %d msg parameters sent, %d expected\n", i, Mpars);
fatal("too many pars in send", "");
}
- for ( ; i < Mpars; i++)
+ for (j = i; i < Mpars; i++)
fprintf(fd, ", 0");
- fprintf(fd, ")");
+ fprintf(fd, ", %d)", j);
if (u_sync)
{ fprintf(fd, ";\n\t\t");
if (u_async)
@@ -2274,7 +2622,7 @@ putstmnt(FILE *fd, Lextok *now, int m)
case 'r':
if (Pid == eventmapnr)
- { fprintf(fd, "if ((ot == EVENT_TRACE && _tp != 'r') ");
+ { fprintf(fd, "if ((II == -EVENT_TRACE && _tp != 'r') ");
putname(fd, "|| _qid+1 != ", now->lft, m, "");
for (v = now->rgt, i=0; v; v = v->rgt, i++)
{ if (v->lft->ntyp != CONST
@@ -2342,10 +2690,13 @@ putstmnt(FILE *fd, Lextok *now, int m)
break;
}
if (has_xu)
- { fprintf(fd, "\n#ifndef XUSAFE\n\t\t");
- putname(fd, "if (q_claim[", now->lft, m, "]&1) ");
- putname(fd, "q_R_check(", now->lft, m, ", II);");
- fprintf(fd, "\n#endif\n\t\t");
+ { fprintf(fd, "\n#if !defined(XUSAFE) && !defined(NOREDUCE)\n\t\t");
+ putname(fd, "if (q_claim[", now->lft, m, "]&1)\n\t\t");
+ putname(fd, "{ q_R_check(", now->lft, m, ", II);\n\t\t");
+ if (has_random && now->val != 0)
+ fprintf(fd, " uerror(\"rand receive on xr channel violates po reduction\");\n\t\t");
+ fprintf(fd, "}\n");
+ fprintf(fd, "#endif\n\t\t");
}
if (u_sync)
{ if (now->val >= 2)
@@ -2398,6 +2749,8 @@ putstmnt(FILE *fd, Lextok *now, int m)
fprintf(fd, "0, %d, 0)) ", i);
Bailout(fd, "");
} }
+ if (has_enabled || has_priority)
+ fprintf(fd, ";\n\t\tif (TstOnly) return 1 /* T2 */");
} else /* random receive: val 1 or 3 */
{ fprintf(fd, ";\n\t\tif (!(XX = Q_has(");
putname(fd, "", now->lft, m, "");
@@ -2415,19 +2768,21 @@ putstmnt(FILE *fd, Lextok *now, int m)
fprintf(fd, ", 0, 0");
fprintf(fd, "))) ");
Bailout(fd, "");
- fprintf(fd, ";\n\t\t");
- if (multi_oval)
- { check_needed();
- fprintf(fd, "(trpt+1)->bup.ovals[%d] = ",
- multi_oval-1);
- multi_oval++;
- } else
- fprintf(fd, "(trpt+1)->bup.oval = ");
- fprintf(fd, "XX");
- }
- if (has_enabled)
- fprintf(fd, ";\n\t\tif (TstOnly) return 1");
+ if (has_enabled || has_priority)
+ fprintf(fd, ";\n\t\tif (TstOnly) return 1 /* T2 */");
+ if (!GenCode) {
+ fprintf(fd, ";\n\t\t");
+ if (multi_oval)
+ { check_needed();
+ fprintf(fd, "(trpt+1)->bup.ovals[%d] = ",
+ multi_oval-1);
+ multi_oval++;
+ } else
+ { fprintf(fd, "(trpt+1)->bup.oval = ");
+ }
+ fprintf(fd, "XX");
+ } }
if (j == 0 && now->val >= 2)
{ fprintf(fd, ";\n\t\t");
@@ -2439,16 +2794,20 @@ putstmnt(FILE *fd, Lextok *now, int m)
fprintf(fd, ";\n\t\t");
/* no variables modified */
if (j == 0 && now->val == 0)
- { fprintf(fd, "if (q_flds[((Q0 *)qptr(");
+ { fprintf(fd, "\n#ifndef BFS_PAR\n\t\t");
+ /* q_flds values are not shared among cores */
+ fprintf(fd, "if (q_flds[((Q0 *)qptr(");
putname(fd, "", now->lft, m, "-1))->_t]");
- fprintf(fd, " != %d)\n\t", i);
- fprintf(fd, "\t\tUerror(\"wrong nr of msg fields in rcv\");\n\t\t");
+ fprintf(fd, " != %d)\n\t\t\t", i);
+ fprintf(fd, "Uerror(\"wrong nr of msg fields in rcv\");\n");
+ fprintf(fd, "#endif\n\t\t");
}
for (v = now->rgt; v; v = v->rgt)
- if ((v->lft->ntyp != CONST
+ { if ((v->lft->ntyp != CONST
&& v->lft->ntyp != EVAL))
- jj++; /* nr of vars needing bup */
+ { jj++; /* nr of vars needing bup */
+ } }
if (jj)
for (v = now->rgt, i = 0; v; v = v->rgt, i++)
@@ -2467,12 +2826,12 @@ putstmnt(FILE *fd, Lextok *now, int m)
sprintf(tempbuf, "(trpt+1)->bup.oval = ");
if (v->lft->sym && !strcmp(v->lft->sym->name, "_"))
- { fprintf(fd, tempbuf);
+ { fprintf(fd, tempbuf, (char *) 0);
putname(fd, "qrecv(", now->lft, m, "");
fprintf(fd, ", XX-1, %d, 0);\n\t\t", i);
} else
{ _isok++;
- cat3(tempbuf, v->lft, ";\n\t\t");
+ cat30(tempbuf, v->lft, ";\n\t\t");
_isok--;
}
}
@@ -2485,7 +2844,7 @@ putstmnt(FILE *fd, Lextok *now, int m)
&& v->lft->ntyp != EVAL
&& v->lft->sym
&& v->lft->sym->type != STRUCT /* not a struct */
- && v->lft->sym->nel == 1 /* not an array */
+ && (v->lft->sym->nel == 1 && v->lft->sym->isarray == 0) /* not array */
&& strcmp(v->lft->sym->name, "_") != 0)
for (w = v->rgt; w; w = w->rgt)
if (v->lft->sym == w->lft->sym)
@@ -2501,6 +2860,7 @@ putstmnt(FILE *fd, Lextok *now, int m)
if (v->lft->ntyp != CONST
&& v->lft->ntyp != EVAL
+ && v->lft->sym != NULL
&& strcmp(v->lft->sym->name, "_") != 0)
{ nocast=1;
_isok++;
@@ -2515,6 +2875,7 @@ putstmnt(FILE *fd, Lextok *now, int m)
if (v->lft->ntyp != CONST
&& v->lft->ntyp != EVAL
+ && v->lft->sym != NULL
&& strcmp(v->lft->sym->name, "_") != 0
&& (v->lft->ntyp != NAME
|| v->lft->sym->type != CHAN))
@@ -2658,8 +3019,10 @@ putstmnt(FILE *fd, Lextok *now, int m)
break;
case ASGN:
- if (has_enabled)
- fprintf(fd, "if (TstOnly) return 1;\n\t\t");
+ if (check_track(now) == STRUCT) { break; }
+
+ if (has_enabled || has_priority)
+ fprintf(fd, "if (TstOnly) return 1; /* T3 */\n\t\t");
_isok++;
if (!GenCode)
@@ -2669,14 +3032,27 @@ putstmnt(FILE *fd, Lextok *now, int m)
sprintf(tempbuf, "(trpt+1)->bup.ovals[%d] = ",
multi_oval-1);
multi_oval++;
- cat3(tempbuf, now->lft, ";\n\t\t");
+ cat30(tempbuf, now->lft, ";\n\t\t");
} else
{ cat3("(trpt+1)->bup.oval = ", now->lft, ";\n\t\t");
} }
+ if (now->lft->sym
+ && now->lft->sym->type == PREDEF
+ && strcmp(now->lft->sym->name, "_") != 0
+ && strcmp(now->lft->sym->name, "_priority") != 0)
+ { fatal("invalid assignment to %s", now->lft->sym->name);
+ }
+
nocast = 1; putstmnt(fd,now->lft,m); nocast = 0;
fprintf(fd," = ");
_isok--;
- putstmnt(fd,now->rgt,m);
+ if (now->lft->sym->isarray
+ && now->rgt->ntyp == ',') /* array initializer */
+ { putstmnt(fd, now->rgt->lft, m);
+ non_fatal("cannot use an array list initializer here", (char *) 0);
+ } else
+ { putstmnt(fd, now->rgt, m);
+ }
if (now->sym->type != CHAN
|| verbose > 0)
@@ -2695,8 +3071,8 @@ putstmnt(FILE *fd, Lextok *now, int m)
break;
case PRINT:
- if (has_enabled)
- fprintf(fd, "if (TstOnly) return 1;\n\t\t");
+ if (has_enabled || has_priority)
+ fprintf(fd, "if (TstOnly) return 1; /* T4 */\n\t\t");
#ifdef PRINTF
fprintf(fd, "printf(%s", now->sym->name);
#else
@@ -2709,8 +3085,8 @@ putstmnt(FILE *fd, Lextok *now, int m)
break;
case PRINTM:
- if (has_enabled)
- fprintf(fd, "if (TstOnly) return 1;\n\t\t");
+ if (has_enabled || has_priority)
+ fprintf(fd, "if (TstOnly) return 1; /* T5 */\n\t\t");
fprintf(fd, "printm(");
if (now->lft && now->lft->ismtyp)
fprintf(fd, "%d", now->lft->val);
@@ -2732,7 +3108,7 @@ putstmnt(FILE *fd, Lextok *now, int m)
case 'q':
if (terse)
- fprintf(fd, "%s", now->sym->name);
+ fprintf(fd, "%s", now->sym?now->sym->name:"?");
else
fprintf(fd, "%d", remotelab(now));
break;
@@ -2748,14 +3124,16 @@ putstmnt(FILE *fd, Lextok *now, int m)
break;
case C_CODE:
- fprintf(fd, "/* %s */\n\t\t", now->sym->name);
- if (has_enabled)
- fprintf(fd, "if (TstOnly) return 1;\n\t\t");
- if (!GenCode) /* not in d_step */
- { fprintf(fd, "sv_save();\n\t\t");
- /* store the old values for reverse moves */
- }
- plunk_inline(fd, now->sym->name, 1);
+ if (now->sym)
+ fprintf(fd, "/* %s */\n\t\t", now->sym->name);
+ if (has_enabled || has_priority)
+ fprintf(fd, "if (TstOnly) return 1; /* T6 */\n\t\t");
+
+ if (now->sym)
+ plunk_inline(fd, now->sym->name, 1, GenCode);
+ else
+ fatal("internal error pangen2.c", (char *) 0);
+
if (!GenCode)
{ fprintf(fd, "\n"); /* state changed, capture it */
fprintf(fd, "#if defined(C_States) && (HAS_TRACK==1)\n");
@@ -2765,10 +3143,10 @@ putstmnt(FILE *fd, Lextok *now, int m)
break;
case ASSERT:
- if (has_enabled)
- fprintf(fd, "if (TstOnly) return 1;\n\t\t");
+ if (has_enabled || has_priority)
+ fprintf(fd, "if (TstOnly) return 1; /* T7 */\n\t\t");
- cat3("assert(", now->lft, ", ");
+ cat3("spin_assert(", now->lft, ", ");
terse = nocast = 1;
cat3("\"", now->lft, "\", II, tt, t)");
terse = nocast = 0;
@@ -2788,7 +3166,7 @@ putstmnt(FILE *fd, Lextok *now, int m)
break;
}
- if (has_enabled)
+ if (has_enabled || has_priority)
{ fprintf(fd, "if (TstOnly)\n\t\t\t");
fprintf(fd, "return (II+1 == now._nr_pr);\n\t\t");
}
@@ -2797,16 +3175,30 @@ putstmnt(FILE *fd, Lextok *now, int m)
break;
default:
- printf("spin: bad node type %d (.m) - line %d\n",
- now->ntyp, now->ln);
- fflush(tm);
+ printf("spin: error, %s:%d, bad node type %d (.m)\n",
+ now->fn->name, now->ln, now->ntyp);
+ fflush(fd);
alldone(1);
}
}
+char *
+simplify_name(char *s)
+{ char *t = s;
+
+ if (!old_scope_rules)
+ { while (*t == '_' || isdigit((int)*t))
+ { t++;
+ } }
+
+ return t;
+}
+
void
putname(FILE *fd, char *pre, Lextok *n, int m, char *suff) /* varref */
{ Symbol *s = n->sym;
+ char *ptr;
+
lineno = n->ln; Fname = n->fn;
if (!s)
@@ -2819,48 +3211,67 @@ putname(FILE *fd, char *pre, Lextok *n, int m, char *suff) /* varref */
{ fprintf(fd, "%s%s%s", pre, n->sym->name, suff);
return;
}
+
if (!s->type) /* not a local name */
s = lookup(s->name); /* must be a global */
if (!s->type)
{ if (strcmp(pre, ".") != 0)
- non_fatal("undeclared variable '%s'", s->name);
+ fatal("undeclared variable '%s'", s->name);
s->type = INT;
}
if (s->type == PROCTYPE)
fatal("proctype-name '%s' used as array-name", s->name);
- fprintf(fd, pre);
+ fprintf(fd, pre, 0);
if (!terse && !s->owner && evalindex != 1)
- { if (s->context
- || strcmp(s->name, "_p") == 0
- || strcmp(s->name, "_pid") == 0)
- { fprintf(fd, "((P%d *)this)->", Pid);
+ { if (old_priority_rules
+ && strcmp(s->name, "_priority") == 0)
+ { fprintf(fd, "1");
+ goto shortcut;
} else
- { int x = strcmp(s->name, "_");
- if (!(s->hidden&1) && x != 0)
- fprintf(fd, "now.");
- if (x == 0 && _isok == 0)
- fatal("attempt to read value of '_'", 0);
- } }
-
- if (withprocname
- && s->context
- && strcmp(pre, "."))
- fprintf(fd, "%s:", s->context->name);
+ { if (s->context
+ || strcmp(s->name, "_p") == 0
+ || strcmp(s->name, "_pid") == 0
+ || strcmp(s->name, "_priority") == 0)
+ { fprintf(fd, "((P%d *)this)->", Pid);
+ } else
+ { int x = strcmp(s->name, "_");
+ if (!(s->hidden&1) && x != 0)
+ fprintf(fd, "now.");
+ if (x == 0 && _isok == 0)
+ fatal("attempt to read value of '_'", 0);
+ } } }
+
+ if (terse && buzzed == 1)
+ { fprintf(fd, "B_state.%s", (s->context)?"local[B_pid].":"");
+ }
+
+ ptr = s->name;
+
+ if (!dont_simplify /* new 6.4.3 */
+ && s->type != PREDEF) /* new 6.0.2 */
+ { if (withprocname
+ && s->context
+ && strcmp(pre, "."))
+ { fprintf(fd, "%s:", s->context->name);
+ ptr = simplify_name(ptr);
+ } else
+ { if (terse)
+ { ptr = simplify_name(ptr);
+ } } }
if (evalindex != 1)
- fprintf(fd, "%s", s->name);
+ fprintf(fd, "%s", ptr);
- if (s->nel != 1)
+ if (s->nel > 1 || s->isarray == 1)
{ if (no_arrays)
- {
- non_fatal("ref to array element invalid in this context",
- (char *)0);
- printf("\thint: instead of, e.g., x[rs] qu[3], use\n");
- printf("\tchan nm_3 = qu[3]; x[rs] nm_3;\n");
- printf("\tand use nm_3 in sends/recvs instead of qu[3]\n");
+ { non_fatal("ref to array element invalid in this context",
+ (char *)0);
+ printf("\thint: instead of, e.g., x[rs] qu[3], use\n");
+ printf("\tchan nm_3 = qu[3]; x[rs] nm_3;\n");
+ printf("\tand use nm_3 in sends/recvs instead of qu[3]\n");
}
/* an xr or xs reference to an array element
* becomes an exclusion tag on the array itself -
@@ -2885,15 +3296,32 @@ putname(FILE *fd, char *pre, Lextok *n, int m, char *suff) /* varref */
|| (!n->lft && s->nel > 0))
{ cat3("[", n->lft, "]");
} else
- { cat3("[ Index(", n->lft, ", ");
+ { /* attempt to catch arrays that are indexed with an array element in the same array
+ * this causes trouble in the verifier in the backtracking
+ * e.g., restoring a[?] in the assignment: a [a[1]] = x where a[1] == 1
+ * but it is hard when the array is inside a structure, so the names dont match
+ */
+#if 0
+ if (n->lft->ntyp == NAME)
+ { printf("%4d: Basename %s index %s\n",
+ n->lft->ln, s->name, n->lft->sym->name);
+ }
+#endif
+ cat3("[ Index(", n->lft, ", ");
fprintf(fd, "%d) ]", s->nel);
- }
- }
- }
+ } }
+ } else
+ { if (n->lft /* effectively a scalar, but with an index */
+ && (n->lft->ntyp != CONST
+ || n->lft->val != 0))
+ { fatal("ref to scalar '%s' using array index", (char *) ptr);
+ } }
+
if (s->type == STRUCT && n->rgt && n->rgt->lft)
{ putname(fd, ".", n->rgt->lft, m, "");
}
- fprintf(fd, suff);
+shortcut:
+ fprintf(fd, suff, 0);
}
void
@@ -2908,7 +3336,11 @@ putremote(FILE *fd, Lextok *n, int m) /* remote reference */
putstmnt(fd, n->lft->lft, m); /* pid */
fprintf(fd, "]");
}
- fprintf(fd, ".%s", n->sym->name);
+ if (ltl_mode)
+ { fprintf(fd, ":%s", n->sym->name);
+ } else
+ { fprintf(fd, ".%s", n->sym->name);
+ }
} else
{ if (Sym_typ(n) < SHORT)
{ promoted = 1;